From 4c87a1868835d05f1cadae7b8ad6a7c95d9d9c0e Mon Sep 17 00:00:00 2001 From: Ross Philipson Date: Tue, 14 Mar 2017 15:40:33 -0400 Subject: Initial commit of EFI TBOOT work from internal project. Signed-off-by: Ross Philipson --- tboot/include/acpi.h | 518 ++++++++++++++ tboot/include/atomic.h | 181 +++++ tboot/include/cmdline.h | 76 ++ tboot/include/com.h | 311 ++++++++ tboot/include/compiler.h | 52 ++ tboot/include/config.h | 133 ++++ tboot/include/ctype.h | 103 +++ tboot/include/efibase.h | 46 ++ tboot/include/eficonfig.h | 109 +++ tboot/include/eficore.h | 134 ++++ tboot/include/hash.h | 123 ++++ tboot/include/integrity.h | 106 +++ tboot/include/io.h | 91 +++ tboot/include/lcp3.h | 282 ++++++++ tboot/include/lcp3_hlp.h | 117 +++ tboot/include/misc.h | 95 +++ tboot/include/mle.h | 96 +++ tboot/include/msr.h | 90 +++ tboot/include/mutex.h | 58 ++ tboot/include/page.h | 66 ++ tboot/include/paging.h | 122 ++++ tboot/include/pci_cfgreg.h | 73 ++ tboot/include/printk.h | 79 ++ tboot/include/processor.h | 340 +++++++++ tboot/include/rijndael.h | 58 ++ tboot/include/sha1.h | 77 ++ tboot/include/sha256.h | 30 + tboot/include/string.h | 73 ++ tboot/include/tb_error.h | 89 +++ tboot/include/tb_policy.h | 388 ++++++++++ tboot/include/tboot.h | 197 +++++ tboot/include/tpm.h | 521 ++++++++++++++ tboot/include/tpm_20.h | 1503 +++++++++++++++++++++++++++++++++++++++ tboot/include/txt/acmod.h | 195 +++++ tboot/include/txt/config_regs.h | 240 +++++++ tboot/include/txt/errorcode.h | 105 +++ tboot/include/txt/heap.h | 377 ++++++++++ tboot/include/txt/mtrrs.h | 149 ++++ tboot/include/txt/smx.h | 171 +++++ tboot/include/txt/txt.h | 76 ++ tboot/include/txt/verify.h | 57 ++ tboot/include/txt/vmcs.h | 346 +++++++++ tboot/include/types.h | 104 +++ tboot/include/uuid.h | 82 +++ tboot/include/vga.h | 87 +++ tboot/include/vmac.h | 168 +++++ 46 files changed, 8494 insertions(+) create mode 100644 tboot/include/acpi.h create mode 100644 tboot/include/atomic.h create mode 100644 tboot/include/cmdline.h create mode 100644 tboot/include/com.h create mode 100644 tboot/include/compiler.h create mode 100644 tboot/include/config.h create mode 100644 tboot/include/ctype.h create mode 100644 tboot/include/efibase.h create mode 100644 tboot/include/eficonfig.h create mode 100644 tboot/include/eficore.h create mode 100644 tboot/include/hash.h create mode 100644 tboot/include/integrity.h create mode 100644 tboot/include/io.h create mode 100644 tboot/include/lcp3.h create mode 100644 tboot/include/lcp3_hlp.h create mode 100644 tboot/include/misc.h create mode 100644 tboot/include/mle.h create mode 100644 tboot/include/msr.h create mode 100644 tboot/include/mutex.h create mode 100644 tboot/include/page.h create mode 100644 tboot/include/paging.h create mode 100644 tboot/include/pci_cfgreg.h create mode 100644 tboot/include/printk.h create mode 100644 tboot/include/processor.h create mode 100644 tboot/include/rijndael.h create mode 100644 tboot/include/sha1.h create mode 100644 tboot/include/sha256.h create mode 100644 tboot/include/string.h create mode 100644 tboot/include/tb_error.h create mode 100644 tboot/include/tb_policy.h create mode 100644 tboot/include/tboot.h create mode 100644 tboot/include/tpm.h create mode 100644 tboot/include/tpm_20.h create mode 100644 tboot/include/txt/acmod.h create mode 100644 tboot/include/txt/config_regs.h create mode 100644 tboot/include/txt/errorcode.h create mode 100644 tboot/include/txt/heap.h create mode 100644 tboot/include/txt/mtrrs.h create mode 100644 tboot/include/txt/smx.h create mode 100644 tboot/include/txt/txt.h create mode 100644 tboot/include/txt/verify.h create mode 100644 tboot/include/txt/vmcs.h create mode 100644 tboot/include/types.h create mode 100644 tboot/include/uuid.h create mode 100644 tboot/include/vga.h create mode 100644 tboot/include/vmac.h (limited to 'tboot/include') diff --git a/tboot/include/acpi.h b/tboot/include/acpi.h new file mode 100644 index 0000000..430b422 --- /dev/null +++ b/tboot/include/acpi.h @@ -0,0 +1,518 @@ +/* $OpenBSD: acpireg.h,v 1.17 2009/04/11 08:22:48 kettenis Exp $ */ +/* + * Copyright (c) 2005 Thorsten Lockert + * Copyright (c) 2005 Marco Peereboom + * + * Permission to use, copy, modify, and distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ +/* + * Portions copyright (c) 2010, Intel Corporation + */ + +#ifndef __ACPI_H__ +#define __ACPI_H__ + +//#define ACPI_DEBUG + +#define RSDP_SCOPE1_LOW (void *)0x000000 +#define RSDP_SCOPE1_HIGH (void *)0x000400 +#define RSDP_SCOPE2_LOW (void *)0x0E0000 +#define RSDP_SCOPE2_HIGH (void *)0x100000 + +/* Root System Descriptor Pointer (RSDP) for ACPI 1.0 */ +struct acpi_rsdp1 { + u_int8_t signature[8]; +#define RSDP_SIG "RSD PTR " + + u_int8_t checksum; /* make sum == 0 */ + u_int8_t oemid[6]; + u_int8_t revision; /* 0 for v1.0, 2 for v2.0 */ + u_int32_t rsdt; /* physical */ +} __packed; + +/* Root System Descriptor Pointer (RSDP) for ACPI 2.0 */ +struct acpi_rsdp { + struct acpi_rsdp1 rsdp1; + /* + * The following values are only valid + * when rsdp_revision == 2 + */ + u_int32_t rsdp_length; /* length of rsdp */ + u_int64_t rsdp_xsdt; /* physical */ + u_int8_t rsdp_extchecksum; /* entire table */ + u_int8_t rsdp_reserved[3]; /* must be zero */ +} __packed; + +/* Common System Description Table Header */ +struct acpi_table_header { + u_int8_t signature[4]; + u_int32_t length; + u_int8_t revision; + u_int8_t checksum; + u_int8_t oemid[6]; + u_int8_t oemtableid[8]; + u_int32_t oemrevision; + + u_int8_t aslcompilerid[4]; + u_int32_t aslcompilerrevision; +} __packed; + +/* Root System Description Table (RSDT) */ +struct acpi_rsdt { + struct acpi_table_header hdr; +#define RSDT_SIG "RSDT" + + u_int32_t table_offsets[1]; +} __packed; + +/* Extended System Descriptiion Table */ +struct acpi_xsdt { + struct acpi_table_header hdr; +#define XSDT_SIG "XSDT" + + u_int64_t table_offsets[1]; +} __packed; + + +/* Generic Address Structure */ +struct acpi_gas { + u_int8_t address_space_id; +#define GAS_SYSTEM_MEMORY 0 +#define GAS_SYSTEM_IOSPACE 1 +#define GAS_PCI_CFG_SPACE 2 +#define GAS_EMBEDDED 3 +#define GAS_SMBUS 4 +#define GAS_FUNCTIONAL_FIXED 127 + u_int8_t register_bit_width; + u_int8_t register_bit_offset; + u_int8_t access_size; +#define GAS_ACCESS_UNDEFINED 0 +#define GAS_ACCESS_BYTE 1 +#define GAS_ACCESS_WORD 2 +#define GAS_ACCESS_DWORD 3 +#define GAS_ACCESS_QWORD 4 + u_int64_t address; +} __packed; + +/* Fixed ACPI Descriptiion Table */ +struct acpi_fadt { + struct acpi_table_header hdr; +#define FADT_SIG "FACP" + + u_int32_t firmware_ctl; /* phys addr FACS */ + u_int32_t dsdt; /* phys addr DSDT */ + + /* int_model is defined in ACPI 1.0, in ACPI 2.0, it should be zero */ + u_int8_t int_model; /* interrupt model (hdr_revision < 3) */ + +#define FADT_INT_DUAL_PIC 0 +#define FADT_INT_MULTI_APIC 1 + u_int8_t pm_profile; /* power mgmt profile */ +#define FADT_PM_UNSPEC 0 +#define FADT_PM_DESKTOP 1 +#define FADT_PM_MOBILE 2 +#define FADT_PM_WORKSTATION 3 +#define FADT_PM_ENT_SERVER 4 +#define FADT_PM_SOHO_SERVER 5 +#define FADT_PM_APPLIANCE 6 +#define FADT_PM_PERF_SERVER 7 + u_int16_t sci_int; /* SCI interrupt */ + u_int32_t smi_cmd; /* SMI command port */ + u_int8_t acpi_enable; /* value to enable */ + u_int8_t acpi_disable; /* value to disable */ + u_int8_t s4bios_req; /* value for S4 */ + u_int8_t pstate_cnt; /* value for performance (hdr_revision > 2) */ + u_int32_t pm1a_evt_blk; /* power management 1a */ + u_int32_t pm1b_evt_blk; /* power mangement 1b */ + u_int32_t pm1a_cnt_blk; /* pm control 1a */ + u_int32_t pm1b_cnt_blk; /* pm control 1b */ + u_int32_t pm2_cnt_blk; /* pm control 2 */ + u_int32_t pm_tmr_blk; + u_int32_t gpe0_blk; + u_int32_t gpe1_blk; + u_int8_t pm1_evt_len; + u_int8_t pm1_cnt_len; + u_int8_t pm2_cnt_len; + u_int8_t pm_tmr_len; + u_int8_t gpe0_blk_len; + u_int8_t gpe1_blk_len; + u_int8_t gpe1_base; + u_int8_t cst_cnt; /* (hdr_revision > 2) */ + u_int16_t p_lvl2_lat; + u_int16_t p_lvl3_lat; + u_int16_t flush_size; + u_int16_t flush_stride; + u_int8_t duty_offset; + u_int8_t duty_width; + u_int8_t day_alrm; + u_int8_t mon_alrm; + u_int8_t century; + u_int16_t iapc_boot_arch; /* (hdr_revision > 2) */ +#define FADT_LEGACY_DEVICES 0x0001 /* Legacy devices supported */ +#define FADT_i8042 0x0002 /* Keyboard controller present */ +#define FADT_NO_VGA 0x0004 /* Do not probe VGA */ + u_int8_t reserved1; + u_int32_t flags; +#define FADT_WBINVD 0x00000001 +#define FADT_WBINVD_FLUSH 0x00000002 +#define FADT_PROC_C1 0x00000004 +#define FADT_P_LVL2_UP 0x00000008 +#define FADT_PWR_BUTTON 0x00000010 +#define FADT_SLP_BUTTON 0x00000020 +#define FADT_FIX_RTC 0x00000040 +#define FADT_RTC_S4 0x00000080 +#define FADT_TMR_VAL_EXT 0x00000100 +#define FADT_DCK_CAP 0x00000200 +#define FADT_RESET_REG_SUP 0x00000400 +#define FADT_SEALED_CASE 0x00000800 +#define FADT_HEADLESS 0x00001000 +#define FADT_CPU_SW_SLP 0x00002000 +#define FADT_PCI_EXP_WAK 0x00004000 +#define FADT_USE_PLATFORM_CLOCK 0x00008000 +#define FADT_S4_RTC_STS_VALID 0x00010000 +#define FADT_REMOTE_POWER_ON_CAPABLE 0x00020000 +#define FADT_FORCE_APIC_CLUSTER_MODEL 0x00040000 +#define FADT_FORCE_APIC_PHYS_DEST_MODE 0x00080000 + /* + * Following values only exist when rev > 1 + * If the extended addresses exists, they + * must be used in preferense to the non- + * extended values above + */ + struct acpi_gas reset_reg; + u_int8_t reset_value; + + u_int8_t reserved2a; + u_int8_t reserved2b; + u_int8_t reserved2c; + + u_int64_t x_firmware_ctl; + u_int64_t x_dsdt; + struct acpi_gas x_pm1a_evt_blk; + struct acpi_gas x_pm1b_evt_blk; + struct acpi_gas x_pm1a_cnt_blk; + struct acpi_gas x_pm1b_cnt_blk; + struct acpi_gas x_pm2_cnt_blk; + struct acpi_gas x_pm_tmr_blk; + struct acpi_gas x_gpe0_blk; + struct acpi_gas x_gpe1_blk; +} __packed; + +struct acpi_madt { + struct acpi_table_header hdr; +#define MADT_SIG "APIC" + + u_int32_t local_apic_address; + u_int32_t flags; +#define ACPI_APIC_PCAT_COMPAT 0x00000001 +} __packed; + +struct acpi_madt_lapic { + u_int8_t apic_type; +#define ACPI_MADT_LAPIC 0 + u_int8_t length; + u_int8_t acpi_proc_id; + u_int8_t apic_id; + u_int32_t flags; +#define ACPI_PROC_ENABLE 0x00000001 +} __packed; + +struct acpi_madt_ioapic { + u_int8_t apic_type; +#define ACPI_MADT_IOAPIC 1 + u_int8_t length; + u_int8_t acpi_ioapic_id; + u_int8_t reserved; + u_int32_t address; + u_int32_t global_int_base; +} __packed; +typedef struct acpi_madt_ioapic acpi_table_ioapic_t; + +struct acpi_madt_override { + u_int8_t apic_type; +#define ACPI_MADT_OVERRIDE 2 + u_int8_t length; + u_int8_t bus; +#define ACPI_OVERRIDE_BUS_ISA 0 + u_int8_t source; + u_int32_t global_int; + u_int16_t flags; +#define ACPI_OVERRIDE_POLARITY_BITS 0x3 +#define ACPI_OVERRIDE_POLARITY_BUS 0x0 +#define ACPI_OVERRIDE_POLARITY_HIGH 0x1 +#define ACPI_OVERRIDE_POLARITY_LOW 0x3 +#define ACPI_OVERRIDE_TRIGGER_BITS 0xc +#define ACPI_OVERRIDE_TRIGGER_BUS 0x0 +#define ACPI_OVERRIDE_TRIGGER_EDGE 0x4 +#define ACPI_OVERRIDE_TRIGGER_LEVEL 0xc +} __packed; + +struct acpi_madt_nmi { + u_int8_t apic_type; +#define ACPI_MADT_NMI 3 + u_int8_t length; + u_int16_t flags; /* Same flags as acpi_madt_override */ + u_int32_t global_int; +} __packed; + +struct acpi_madt_lapic_nmi { + u_int8_t apic_type; +#define ACPI_MADT_LAPIC_NMI 4 + u_int8_t length; + u_int8_t acpi_proc_id; + u_int16_t flags; /* Same flags as acpi_madt_override */ + u_int8_t local_apic_lint; +} __packed; + +struct acpi_madt_lapic_override { + u_int8_t apic_type; +#define ACPI_MADT_LAPIC_OVERRIDE 5 + u_int8_t length; + u_int16_t reserved; + u_int64_t lapic_address; +} __packed; + +struct acpi_madt_io_sapic { + u_int8_t apic_type; +#define ACPI_MADT_IO_SAPIC 6 + u_int8_t length; + u_int8_t iosapic_id; + u_int8_t reserved; + u_int32_t global_int_base; + u_int64_t iosapic_address; +} __packed; + +struct acpi_madt_local_sapic { + u_int8_t apic_type; +#define ACPI_MADT_LOCAL_SAPIC 7 + u_int8_t length; + u_int8_t acpi_proc_id; + u_int8_t local_sapic_id; + u_int8_t local_sapic_eid; + u_int8_t reserved[3]; + u_int32_t flags; /* Same flags as acpi_madt_lapic */ + u_int32_t acpi_proc_uid; + u_int8_t acpi_proc_uid_string[1]; +} __packed; + +struct acpi_madt_platform_int { + u_int8_t apic_type; +#define ACPI_MADT_PLATFORM_INT 8 + u_int8_t length; + u_int16_t flags; /* Same flags as acpi_madt_override */ + u_int8_t int_type; +#define ACPI_MADT_PLATFORM_PMI 1 +#define ACPI_MADT_PLATFORM_INIT 2 +#define ACPI_MADT_PLATFORM_CORR_ERROR 3 + u_int8_t proc_id; + u_int8_t proc_eid; + u_int8_t io_sapic_vec; + u_int32_t global_int; + u_int32_t platform_int_flags; +#define ACPI_MADT_PLATFORM_CPEI 0x00000001 +} __packed; + +union acpi_madt_entry { + struct acpi_madt_lapic madt_lapic; + struct acpi_madt_ioapic madt_ioapic; + struct acpi_madt_override madt_override; + struct acpi_madt_nmi madt_nmi; + struct acpi_madt_lapic_nmi madt_lapic_nmi; + struct acpi_madt_lapic_override madt_lapic_override; + struct acpi_madt_io_sapic madt_io_sapic; + struct acpi_madt_local_sapic madt_local_sapic; + struct acpi_madt_platform_int madt_platform_int; +} __packed; + +struct device_scope { + u_int8_t type; + u_int8_t length; + u_int16_t reserved; + u_int8_t enumeration_id; + u_int8_t start_bus_number; + u_int16_t path[1]; /* Path starts here */ +} __packed; + +struct dmar_remapping { + u_int16_t type; +#define DMAR_REMAPPING_DRHD 0 +#define DMAR_REMAPPING_RMRR 1 +#define DMAR_REMAPPING_ATSR 2 +#define DMAR_REMAPPING_RHSA 3 +#define DMAR_REMAPPING_RESERVED 4 + u_int16_t length; + u_int8_t flags; +#define REMAPPING_INCLUDE_PCI_ALL Ox01 + + u_int8_t reserved; + u_int16_t segment_number; + u_int8_t register_base_address[8]; + struct device_scope device_scope_entry[1]; /* Device Scope starts here */ +} __packed; + +struct acpi_dmar { + struct acpi_table_header hdr; +#define DMAR_SIG "DMAR" + u_int8_t host_address_width; + u_int8_t flags; +#define DMAR_INTR_REMAP 0x01 + + u_int8_t reserved[10]; + struct dmar_remapping table_offsets[1]; /* dmar_remapping structure starts here */ +} __packed; + +struct acpi_mcfg_mmcfg { + u_int64_t base_address; + u_int16_t group_number; + u_int8_t start_bus_number; + u_int8_t end_bus_number; + u_int32_t reserved; +} __packed; + +struct acpi_mcfg { + struct acpi_table_header hdr; +#define MCFG_SIG "MCFG" + + u_int64_t reserved; + /* struct acpi_mcfg_mmcfg table_offsets[1]; */ + u_int32_t base_address; +} __packed; +typedef struct acpi_mcfg acpi_table_mcfg_t; + +#if 0 + +#define ACPI_FREQUENCY 3579545 /* Per ACPI spec */ + +/* + * PCI Configuration space + */ +#define ACPI_PCI_BUS(addr) (u_int16_t)((addr) >> 48) +#define ACPI_PCI_DEV(addr) (u_int16_t)((addr) >> 32) +#define ACPI_PCI_FN(addr) (u_int16_t)((addr) >> 16) +#define ACPI_PCI_REG(addr) (u_int16_t)(addr) +#define ACPI_PCI_ADDR(b,d,f,r) ((u_int64_t)(b)<<48LL | (u_int64_t)(d)<<32LL | (f)<<16LL | (r)) + +/* + * PM1 Status Registers Fixed Hardware Feature Status Bits + */ +#define ACPI_PM1_STATUS 0x00 +#define ACPI_PM1_TMR_STS 0x0001 +#define ACPI_PM1_BM_STS 0x0010 +#define ACPI_PM1_GBL_STS 0x0020 +#define ACPI_PM1_PWRBTN_STS 0x0100 +#define ACPI_PM1_SLPBTN_STS 0x0200 +#define ACPI_PM1_RTC_STS 0x0400 +#define ACPI_PM1_PCIEXP_WAKE_STS 0x4000 +#define ACPI_PM1_WAK_STS 0x8000 + +/* + * PM1 Enable Registers + */ +#define ACPI_PM1_ENABLE 0x02 +#define ACPI_PM1_TMR_EN 0x0001 +#define ACPI_PM1_GBL_EN 0x0020 +#define ACPI_PM1_PWRBTN_EN 0x0100 +#define ACPI_PM1_SLPBTN_EN 0x0200 +#define ACPI_PM1_RTC_EN 0x0400 +#define ACPI_PM1_PCIEXP_WAKE_DIS 0x4000 + +/* + * PM1 Control Registers + */ +#define ACPI_PM1_CONTROL 0x00 +#define ACPI_PM1_SCI_EN 0x0001 +#define ACPI_PM1_BM_RLD 0x0002 +#define ACPI_PM1_GBL_RLS 0x0004 +#define ACPI_PM1_SLP_TYPX(x) ((x) << 10) +#define ACPI_PM1_SLP_TYPX_MASK 0x1c00 +#define ACPI_PM1_SLP_EN 0x2000 + +/* + * PM2 Control Registers + */ +#define ACPI_PM2_CONTROL 0x06 +#define ACPI_PM2_ARB_DIS 0x0001 + + +/* + * Sleeping States + */ +#define ACPI_STATE_S0 0 +#define ACPI_STATE_S1 1 +#define ACPI_STATE_S2 2 +#define ACPI_STATE_S3 3 +#define ACPI_STATE_S4 4 +#define ACPI_STATE_S5 5 + +/* + * ACPI Device IDs + */ +#define ACPI_DEV_TIM "PNP0100" /* System timer */ +#define ACPI_DEV_ACPI "PNP0C08" /* ACPI device */ +#define ACPI_DEV_PCIB "PNP0A03" /* PCI bus */ +#define ACPI_DEV_GISAB "PNP0A05" /* Generic ISA Bus */ +#define ACPI_DEV_EIOB "PNP0A06" /* Extended I/O Bus */ +#define ACPI_DEV_PCIEB "PNP0A08" /* PCIe bus */ +#define ACPI_DEV_MR "PNP0C02" /* Motherboard resources */ +#define ACPI_DEV_NPROC "PNP0C04" /* Numeric data processor */ +#define ACPI_DEV_CS "PNP0C08" /* ACPI-Compliant System */ +#define ACPI_DEV_ECD "PNP0C09" /* Embedded Controller Device */ +#define ACPI_DEV_CMB "PNP0C0A" /* Control Method Battery */ +#define ACPI_DEV_FAN "PNP0C0B" /* Fan Device */ +#define ACPI_DEV_PBD "PNP0C0C" /* Power Button Device */ +#define ACPI_DEV_LD "PNP0C0D" /* Lid Device */ +#define ACPI_DEV_SBD "PNP0C0E" /* Sleep Button Device */ +#define ACPI_DEV_PILD "PNP0C0F" /* PCI Interrupt Link Device */ +#define ACPI_DEV_MEMD "PNP0C80" /* Memory Device */ +#define ACPI_DEV_SHC "ACPI0001" /* SMBus 1.0 Host Controller */ +#define ACPI_DEV_SMS1 "ACPI0002" /* Smart Battery Subsystem */ +#define ACPI_DEV_AC "ACPI0003" /* AC Device */ +#define ACPI_DEV_MD "ACPI0004" /* Module Device */ +#define ACPI_DEV_SMS2 "ACPI0005" /* SMBus 2.0 Host Controller */ +#define ACPI_DEV_GBD "ACPI0006" /* GPE Block Device */ +#define ACPI_DEV_PD "ACPI0007" /* Processor Device */ +#define ACPI_DEV_ALSD "ACPI0008" /* Ambient Light Sensor Device */ +#define ACPI_DEV_IOXA "ACPI0009" /* IO x APIC Device */ +#define ACPI_DEV_IOA "ACPI000A"/ /* IO APIC Device */ +#define ACPI_DEV_IOSA "ACPI000B" /* IO SAPIC Device */ +#define ACPI_DEV_THZ "THERMALZONE" /* Thermal Zone */ +#define ACPI_DEV_FFB "FIXEDBUTTON" /* Fixed Feature Button */ +#define ACPI_DEV_ASUS "ASUS010" /* ASUS Hotkeys */ +#define ACPI_DEV_THINKPAD "IBM0068" /* ThinkPad support */ + +#endif + +bool save_vtd_dmar_table(void); +bool restore_vtd_dmar_table(void); +bool remove_vtd_dmar_table(void); + +struct acpi_table_ioapic *get_acpi_ioapic_table(void); +struct acpi_mcfg *get_acpi_mcfg_table(void); +void disable_smis(void); + +bool machine_sleep(const tboot_acpi_sleep_info_t *); +void set_s3_resume_vector(const tboot_acpi_sleep_info_t *, uint64_t); +struct acpi_rsdp *get_rsdp(void); +uint32_t get_madt_apic_base(void); + +#endif /* __ACPI_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/atomic.h b/tboot/include/atomic.h new file mode 100644 index 0000000..502cc36 --- /dev/null +++ b/tboot/include/atomic.h @@ -0,0 +1,181 @@ +/*- + * Copyright (c) 1998 Doug Rabson + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * $FreeBSD: src/sys/i386/include/atomic.h,v 1.47.2.2.2.1 2010/02/10 00:26:20 kensmith Exp $ + */ +/* + * Portions copyright (c) 2010, Intel Corporation + */ + +#ifndef __ATOMIC_H__ +#define __ATOMIC_H__ + +/* + * Various simple operations on memory, each of which is atomic in the + * presence of interrupts and multiple processors. + * + * atomic_set_char(P, V) (*(u_char *)(P) |= (V)) + * atomic_clear_char(P, V) (*(u_char *)(P) &= ~(V)) + * atomic_add_char(P, V) (*(u_char *)(P) += (V)) + * atomic_subtract_char(P, V) (*(u_char *)(P) -= (V)) + * + * atomic_set_short(P, V) (*(u_short *)(P) |= (V)) + * atomic_clear_short(P, V) (*(u_short *)(P) &= ~(V)) + * atomic_add_short(P, V) (*(u_short *)(P) += (V)) + * atomic_subtract_short(P, V) (*(u_short *)(P) -= (V)) + * + * atomic_set_int(P, V) (*(u_int *)(P) |= (V)) + * atomic_clear_int(P, V) (*(u_int *)(P) &= ~(V)) + * atomic_add_int(P, V) (*(u_int *)(P) += (V)) + * atomic_subtract_int(P, V) (*(u_int *)(P) -= (V)) + * atomic_readandclear_int(P) (return (*(u_int *)(P)); *(u_int *)(P) = 0;) + * + * atomic_set_long(P, V) (*(u_long *)(P) |= (V)) + * atomic_clear_long(P, V) (*(u_long *)(P) &= ~(V)) + * atomic_add_long(P, V) (*(u_long *)(P) += (V)) + * atomic_subtract_long(P, V) (*(u_long *)(P) -= (V)) + * atomic_readandclear_long(P) (return (*(u_long *)(P)); *(u_long *)(P) = 0;) + */ + +/* + * The above functions are expanded inline in the statically-linked + * kernel. Lock prefixes are generated if an SMP kernel is being + * built. + * + * Kernel modules call real functions which are built into the kernel. + * This allows kernel modules to be portable between UP and SMP systems. + */ + +/* all operations will be defined only for 'int's */ +#define atomic_t u_int + +#define MPLOCKED "lock ; " + +/* + * The assembly is volatilized to avoid code chunk removal by the compiler. + * GCC aggressively reorders operations and memory clobbering is necessary + * in order to avoid that for memory barriers. + */ +#define ATOMIC_ASM(NAME, TYPE, OP, CONS, V) \ +static __inline void \ +atomic_##NAME##_##TYPE(volatile u_##TYPE *p, u_##TYPE v)\ +{ \ + __asm __volatile(MPLOCKED OP \ + : "=m" (*p) \ + : CONS (V), "m" (*p)); \ +} \ + \ +static __inline void \ +atomic_##NAME##_barr_##TYPE(volatile u_##TYPE *p, u_##TYPE v)\ +{ \ + __asm __volatile(MPLOCKED OP \ + : "=m" (*p) \ + : CONS (V), "m" (*p) \ + : "memory"); \ +} \ +struct __hack + +/* + * Atomically add the value of v to the integer pointed to by p and return + * the previous value of *p. + */ +static __inline u_int +atomic_fetchadd_int(volatile u_int *p, u_int v) +{ + + __asm __volatile( + " " MPLOCKED " " + " xaddl %0, %1 ; " + "# atomic_fetchadd_int" + : "+r" (v), /* 0 (result) */ + "=m" (*p) /* 1 */ + : "m" (*p)); /* 2 */ + + return (v); +} + +#define ATOMIC_STORE_LOAD(TYPE, LOP, SOP) \ +static __inline u_##TYPE \ +atomic_load_acq_##TYPE(volatile u_##TYPE *p) \ +{ \ + u_##TYPE res; \ + \ + __asm __volatile(MPLOCKED LOP \ + : "=a" (res), /* 0 */ \ + "=m" (*p) /* 1 */ \ + : "m" (*p) /* 2 */ \ + : "memory"); \ + \ + return (res); \ +} \ + \ +/* \ + * The XCHG instruction asserts LOCK automagically. \ + */ \ +static __inline void \ +atomic_store_rel_##TYPE(volatile u_##TYPE *p, u_##TYPE v)\ +{ \ + __asm __volatile(SOP \ + : "=m" (*p), /* 0 */ \ + "+r" (v) /* 1 */ \ + : "m" (*p) /* 2 */ \ + : "memory"); \ +} \ +struct __hack + +ATOMIC_ASM(set, int, "orl %1,%0", "ir", v); +ATOMIC_ASM(clear, int, "andl %1,%0", "ir", ~v); +ATOMIC_ASM(add, int, "addl %1,%0", "ir", v); +ATOMIC_ASM(subtract, int, "subl %1,%0", "ir", v); + +ATOMIC_STORE_LOAD(int, "cmpxchgl %0,%1", "xchgl %1,%0"); + +#undef ATOMIC_ASM +#undef ATOMIC_STORE_LOAD + +/* Read the current value and store a zero in the destination. */ +static __inline u_int +atomic_readandclear_int(volatile u_int *addr) +{ + u_int res; + + res = 0; + __asm __volatile( + " xchgl %1,%0 ; " + "# atomic_readandclear_int" + : "+r" (res), /* 0 */ + "=m" (*addr) /* 1 */ + : "m" (*addr)); + + return (res); +} + + +#define atomic_read(atom) atomic_load_acq_int(atom) +#define atomic_inc(atom) atomic_add_int((atom), 1) +#define atomic_dec(atom) atomic_subtract_int((atom), 1) +#define atomic_set(atom, val) atomic_set_int((atom), (val)) + +#endif /* __ATOMIC_H__ */ diff --git a/tboot/include/cmdline.h b/tboot/include/cmdline.h new file mode 100644 index 0000000..4b01c20 --- /dev/null +++ b/tboot/include/cmdline.h @@ -0,0 +1,76 @@ +/* + * cmdline.h: support functions for command line parsing + * + * Copyright (c) 2006-2010, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __CMDLINE_H__ +#define __CMDLINE_H__ + +#define CMDLINE_SIZE 512 +char g_cmdline[CMDLINE_SIZE]; + + +void tboot_parse_cmdline(bool defaults); +void get_tboot_loglvl(void); +void get_tboot_log_targets(void); +bool get_tboot_serial(void); +void get_tboot_baud(void); +void get_tboot_fmt(void); +void get_tboot_vga_delay(void); +bool get_tboot_mwait(void); +bool get_tboot_prefer_da(void); +void get_tboot_min_ram(void); +bool get_tboot_call_racm(void); +bool get_tboot_call_racm_check(void); +bool get_tboot_measure_nv(void); +void get_tboot_extpol(void); + +/* for parse cmdline of linux kernel, say vga and mem */ +void linux_parse_cmdline(const char *cmdline); +bool get_linux_vga(int *vid_mode); +bool get_linux_mem(uint64_t *initrd_max_mem); + +uint8_t get_loglvl_prefix(char **pbuf, int *len); + +#endif /* __CMDLINE_H__ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/com.h b/tboot/include/com.h new file mode 100644 index 0000000..c51a9fd --- /dev/null +++ b/tboot/include/com.h @@ -0,0 +1,311 @@ +/*- + * Copyright (c) 1991 The Regents of the University of California. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 4. Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * from: @(#)ns16550.h 7.1 (Berkeley) 5/9/91 + * $FreeBSD: src/sys/dev/ic/ns16550.h,v 1.20 2010/01/11 04:13:06 imp Exp $ + */ +/* + * Portions copyright (c) 2010, Intel Corporation + */ + +/* + * NS8250... UART registers. + */ +#ifndef __COM_H__ +#define __COM_H__ + +/* 8250 registers #[0-6]. */ + +#define com_data 0 /* data register (R/W) */ +#define REG_DATA com_data + +#define com_ier 1 /* interrupt enable register (W) */ +#define REG_IER com_ier +#define IER_ERXRDY 0x1 +#define IER_ETXRDY 0x2 +#define IER_ERLS 0x4 +#define IER_EMSC 0x8 + +#define IER_BITS "\20\1ERXRDY\2ETXRDY\3ERLS\4EMSC" + +#define com_iir 2 /* interrupt identification register (R) */ +#define REG_IIR com_iir +#define IIR_IMASK 0xf +#define IIR_RXTOUT 0xc +#define IIR_BUSY 0x7 +#define IIR_RLS 0x6 +#define IIR_RXRDY 0x4 +#define IIR_TXRDY 0x2 +#define IIR_NOPEND 0x1 +#define IIR_MLSC 0x0 +#define IIR_FIFO_MASK 0xc0 /* set if FIFOs are enabled */ + +#define IIR_BITS "\20\1NOPEND\2TXRDY\3RXRDY" + +#define com_lcr 3 /* line control register (R/W) */ +#define com_cfcr com_lcr /* character format control register (R/W) */ +#define REG_LCR com_lcr +#define LCR_DLAB 0x80 +#define CFCR_DLAB LCR_DLAB +#define LCR_EFR_ENABLE 0xbf /* magic to enable EFR on 16650 up */ +#define CFCR_EFR_ENABLE LCR_EFR_ENABLE +#define LCR_SBREAK 0x40 +#define CFCR_SBREAK LCR_SBREAK +#define LCR_PZERO 0x30 +#define CFCR_PZERO LCR_PZERO +#define LCR_PONE 0x20 +#define CFCR_PONE LCR_PONE +#define LCR_PEVEN 0x10 +#define CFCR_PEVEN LCR_PEVEN +#define LCR_PODD 0x00 +#define CFCR_PODD LCR_PODD +#define LCR_PENAB 0x08 +#define CFCR_PENAB LCR_PENAB +#define LCR_STOPB 0x04 +#define CFCR_STOPB LCR_STOPB +#define LCR_8BITS 0x03 +#define CFCR_8BITS LCR_8BITS +#define LCR_7BITS 0x02 +#define CFCR_7BITS LCR_7BITS +#define LCR_6BITS 0x01 +#define CFCR_6BITS LCR_6BITS +#define LCR_5BITS 0x00 +#define CFCR_5BITS LCR_5BITS + +#define LCR_ODD_PARITY (LCR_PENAB | LCR_PODD) +#define LCR_EVEN_PARITY (LCR_PENAB | LCR_PEVEN) +#define LCR_MARK_PARITY (LCR_PENAB | LCR_PONE) +#define LCR_SPACE_PARITY (LCR_PENAB | LCR_PZERO) + +#define com_mcr 4 /* modem control register (R/W) */ +#define REG_MCR com_mcr +#define MCR_PRESCALE 0x80 /* only available on 16650 up */ +#define MCR_LOOPBACK 0x10 +#define MCR_IE 0x08 +#define MCR_IENABLE MCR_IE +#define MCR_DRS 0x04 +#define MCR_RTS 0x02 +#define MCR_DTR 0x01 + +#define MCR_BITS "\20\1DTR\2RTS\3DRS\4IE\5LOOPBACK\10PRESCALE" + +#define com_lsr 5 /* line status register (R/W) */ +#define REG_LSR com_lsr +#define LSR_RCV_FIFO 0x80 +#define LSR_TEMT 0x40 +#define LSR_TSRE LSR_TEMT +#define LSR_THRE 0x20 +#define LSR_TXRDY LSR_THRE +#define LSR_BI 0x10 +#define LSR_FE 0x08 +#define LSR_PE 0x04 +#define LSR_OE 0x02 +#define LSR_RXRDY 0x01 +#define LSR_RCV_MASK 0x1f + +#define LSR_BITS "\20\1RXRDY\2OE\3PE\4FE\5BI\6THRE\7TEMT\10RCV_FIFO" + +#define com_msr 6 /* modem status register (R/W) */ +#define REG_MSR com_msr +#define MSR_DCD 0x80 +#define MSR_RI 0x40 +#define MSR_DSR 0x20 +#define MSR_CTS 0x10 +#define MSR_DDCD 0x08 +#define MSR_TERI 0x04 +#define MSR_DDSR 0x02 +#define MSR_DCTS 0x01 + +#define MSR_BITS "\20\1DCTS\2DDSR\3TERI\4DDCD\5CTS\6DSR\7RI\10DCD" + +/* 8250 multiplexed registers #[0-1]. Access enabled by LCR[7]. */ +#define com_dll 0 /* divisor latch low (R/W) */ +#define com_dlbl com_dll +#define com_dlm 1 /* divisor latch high (R/W) */ +#define com_dlbh com_dlm +#define REG_DLL com_dll +#define REG_DLH com_dlm + +/* 16450 register #7. Not multiplexed. */ +#define com_scr 7 /* scratch register (R/W) */ + +/* 16550 register #2. Not multiplexed. */ +#define com_fcr 2 /* FIFO control register (W) */ +#define com_fifo com_fcr +#define REG_FCR com_fcr +#define FCR_ENABLE 0x01 +#define FIFO_ENABLE FCR_ENABLE +#define FCR_RCV_RST 0x02 +#define FIFO_RCV_RST FCR_RCV_RST +#define FCR_XMT_RST 0x04 +#define FIFO_XMT_RST FCR_XMT_RST +#define FCR_DMA 0x08 +#define FIFO_DMA_MODE FCR_DMA +#define FCR_RX_LOW 0x00 +#define FIFO_RX_LOW FCR_RX_LOW +#define FCR_RX_MEDL 0x40 +#define FIFO_RX_MEDL FCR_RX_MEDL +#define FCR_RX_MEDH 0x80 +#define FIFO_RX_MEDH FCR_RX_MEDH +#define FCR_RX_HIGH 0xc0 +#define FIFO_RX_HIGH FCR_RX_HIGH + +#define FCR_BITS "\20\1ENABLE\2RCV_RST\3XMT_RST\4DMA" + +/* 16650 registers #2,[4-7]. Access enabled by LCR_EFR_ENABLE. */ + +#define com_efr 2 /* enhanced features register (R/W) */ +#define REG_EFR com_efr +#define EFR_CTS 0x80 +#define EFR_AUTOCTS EFR_CTS +#define EFR_RTS 0x40 +#define EFR_AUTORTS EFR_RTS +#define EFR_EFE 0x10 /* enhanced functions enable */ + +#define com_xon1 4 /* XON 1 character (R/W) */ +#define com_xon2 5 /* XON 2 character (R/W) */ +#define com_xoff1 6 /* XOFF 1 character (R/W) */ +#define com_xoff2 7 /* XOFF 2 character (R/W) */ + +#define com_usr 39 /* Octeon 16750/16550 Uart Status Reg */ +#define REG_USR com_usr +#define USR_TXFIFO_NOTFULL 2 /* Uart TX FIFO Not full */ + +/* 16950 register #1. Access enabled by ACR[7]. Also requires !LCR[7]. */ +#define com_asr 1 /* additional status register (R[0-7]/W[0-1]) */ + +/* 16950 register #3. R/W access enabled by ACR[7]. */ +#define com_rfl 3 /* receiver fifo level (R) */ + +/* + * 16950 register #4. Access enabled by ACR[7]. Also requires + * !LCR_EFR_ENABLE. + */ +#define com_tfl 4 /* transmitter fifo level (R) */ + +/* + * 16950 register #5. Accessible if !LCR_EFR_ENABLE. Read access also + * requires ACR[6]. + */ +#define com_icr 5 /* index control register (R/W) */ + +/* + * 16950 register #7. It is the same as com_scr except it has a different + * abbreviation in the manufacturer's data sheet and it also serves as an + * index into the Indexed Control register set. + */ +#define com_spr com_scr /* scratch pad (and index) register (R/W) */ +#define REG_SPR com_scr + +/* + * 16950 indexed control registers #[0-0x13]. Access is via index in SPR, + * data in ICR (if ICR is accessible). + */ + +#define com_acr 0 /* additional control register (R/W) */ +#define ACR_ASE 0x80 /* ASR/RFL/TFL enable */ +#define ACR_ICRE 0x40 /* ICR enable */ +#define ACR_TLE 0x20 /* TTL/RTL enable */ + +#define com_cpr 1 /* clock prescaler register (R/W) */ +#define com_tcr 2 /* times clock register (R/W) */ +#define com_ttl 4 /* transmitter trigger level (R/W) */ +#define com_rtl 5 /* receiver trigger level (R/W) */ +/* ... */ + +/* Hardware extension mode register for RSB-2000/3000. */ +#define com_emr com_msr +#define EMR_EXBUFF 0x04 +#define EMR_CTSFLW 0x08 +#define EMR_DSRFLW 0x10 +#define EMR_RTSFLW 0x20 +#define EMR_DTRFLW 0x40 +#define EMR_EFMODE 0x80 + +/* com port */ +#define COM1_ADDR 0x3f8 +#define COM2_ADDR 0x2f8 +#define COM3_ADDR 0x3e8 +#define COM4_ADDR 0x2e8 + +#define GET_LCR_DATABIT(x) ({ \ + typeof(x) val = 0; \ + val = (((x) == 5) ? LCR_5BITS : (val)); \ + val = (((x) == 6) ? LCR_6BITS : (val)); \ + val = (((x) == 7) ? LCR_7BITS : (val)); \ + val = (((x) == 8) ? LCR_8BITS : (val)); \ + val; }) + +#define GET_LCR_STOPBIT(x) ({ \ + typeof(x) val = 0; \ + val = (((x) > 1) ? LCR_STOPB : val); \ + val; }) + +#define GET_LCR_PARITY(x) ({ \ + typeof(x) val = 0; \ + val = (((x) == 'n') ? (!LCR_PENAB) : val); \ + val = (((x) == 'o') ? LCR_ODD_PARITY : val); \ + val = (((x) == 'e') ? LCR_EVEN_PARITY : val); \ + val = (((x) == 'm') ? LCR_MARK_PARITY : val); \ + val = (((x) == 's') ? LCR_SPACE_PARITY : val); \ + val; }) + +#define GET_LCR_VALUE(data, stop, parity) \ + (GET_LCR_DATABIT(data) | GET_LCR_STOPBIT(stop) | GET_LCR_PARITY(parity)) + +typedef struct __packed { + uint32_t bus; + uint32_t slot; + uint32_t func; +} bdf_t; + +typedef struct __packed { + uint32_t comc_curspeed; /* baud rate */ + uint32_t comc_clockhz; /* clock hz */ + uint8_t comc_fmt; /* lcr value */ + uint32_t comc_port; /* serial port, COM[1|2|3|4] */ + uint32_t comc_irq; /* irq */ + bdf_t comc_psbdf; /* PCI serial controller bdf */ + bdf_t comc_pbbdf; /* PCI bridge bdf */ +} serial_port_t; + +void comc_init(void); +void comc_puts(const char*, unsigned int); + +#endif /* __COM_H__ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/compiler.h b/tboot/include/compiler.h new file mode 100644 index 0000000..8987161 --- /dev/null +++ b/tboot/include/compiler.h @@ -0,0 +1,52 @@ +/* + * compiler.h: These are various compiler-related defines + * + * Copyright (c) 2010, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __COMPILER_H__ +#define __COMPILER_H__ + +#define inline __inline__ +#define always_inline __inline__ __attribute__ ((always_inline)) + +#endif /* __COMPILER_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/config.h b/tboot/include/config.h new file mode 100644 index 0000000..9f9d8d1 --- /dev/null +++ b/tboot/include/config.h @@ -0,0 +1,133 @@ +/* + * config.h: project-wide definitions + * + * Copyright (c) 2006-2010, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef __CONFIG_H__ +#define __CONFIG_H__ + +/* EFI and MLE layout values */ +/* TODO MLE should cover .rdata too. Address that later */ + +/********************************************************** + * TBOOT rumtime layout + * + * +---------------+ 0xXXXX0000 + * | | Post Launch page tables + * | PLETP | 4K pages below 2M + * | | 2M pages below 4G + * +---------------+ 0xXXXX7000 + * | MLEPT | Measure Launch page tables + * | | Cover MLE/.text section + * +---------------+ 0xXXXXA000 + * | PE HDR | + * +---------------+ 0xXXXXB000 + * | | + * | MLE | The MLE/.text section. + * | | + * +---------------+ + * | | + * | DATA | + * | SHATED | The rest of the TBOOT image. + * | ETC | + * | | + * +---------------+ + * + **********************************************************/ + +/* Somewhere just below 4G */ +#define TBOOT_MAX_IMAGE_MEM 0xfffff000 + +/* TBOOT post launch page table block */ +#define TBOOT_PLEPT_COUNT (7) +#define TBOOT_PLEPT_SIZE (TBOOT_PLEPT_COUNT*PAGE_SIZE) + +/* TBOOT MLE page table block */ +#define TBOOT_MLEPT_COUNT (3) +#define TBOOT_MLEPT_SIZE (TBOOT_MLEPT_COUNT*PAGE_SIZE) + +/* Totals */ +#define TBOOT_RTMEM_COUNT (TBOOT_PLEPT_COUNT + TBOOT_MLEPT_COUNT) +#define TBOOT_RTMEM_SIZE (TBOOT_PLEPT_SIZE + TBOOT_MLEPT_SIZE) + +#ifndef NR_CPUS +#define NR_CPUS 512 +#endif + +#ifdef __ASSEMBLY__ +#define ENTRY(name) \ + .globl name; \ + .align 16,0x90; \ + name: +#endif + +#define COMPILE_TIME_ASSERT(e) \ +{ \ + struct tmp { \ + int a : ((e) ? 1 : -1); \ + }; \ +} + +#define __data __attribute__ ((__section__ (".data#"))) +#define __text __attribute__ ((__section__ (".text#"))) + +#define __packed __attribute__ ((packed)) + +/* tboot log level */ +#ifdef NO_TBOOT_LOGLVL +#define TBOOT_NONE +#define TBOOT_ERR +#define TBOOT_WARN +#define TBOOT_INFO +#define TBOOT_DETA +#define TBOOT_ALL +#else /* NO_TBOOT_LOGLVL */ +#define TBOOT_NONE "<0>" +#define TBOOT_ERR "<1>" +#define TBOOT_WARN "<2>" +#define TBOOT_INFO "<3>" +#define TBOOT_DETA "<4>" +#define TBOOT_ALL "<5>" +#endif /* NO_TBOOT_LOGLVL */ + +#endif /* __CONFIG_H__ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/ctype.h b/tboot/include/ctype.h new file mode 100644 index 0000000..20d6769 --- /dev/null +++ b/tboot/include/ctype.h @@ -0,0 +1,103 @@ +/* + * Copyright (c) 2010, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __CTYPE_H__ +#define __CTYPE_H__ + +#include +#include +#include + +/* from: + * http://fxr.watson.org/fxr/source/dist/acpica/acutils.h?v=NETBSD5 +*/ +#define CTYPE_SIZE 257 +const uint8_t _ctype[CTYPE_SIZE]; + +#define _XA 0x00 /* extra alphabetic - not supported */ +#define _XS 0x40 /* extra space */ +#define _BB 0x00 /* BEL, BS, etc. - not supported */ +#define _CN 0x20 /* CR, FF, HT, NL, VT */ +#define _DI 0x04 /* ''-'9' */ +#define _LO 0x02 /* 'a'-'z' */ +#define _PU 0x10 /* punctuation */ +#define _SP 0x08 /* space */ +#define _UP 0x01 /* 'A'-'Z' */ +#define _XD 0x80 /* ''-'9', 'A'-'F', 'a'-'f' */ + +static always_inline bool isdigit(int c) +{ + return (_ctype[(unsigned char)(c)] & (_DI)); +} +static always_inline bool isspace(int c) +{ + return (_ctype[(unsigned char)(c)] & (_SP)); +} +static always_inline bool isxdigit(int c) +{ + return (_ctype[(unsigned char)(c)] & (_XD)); +} +static always_inline bool isupper(int c) +{ + return (_ctype[(unsigned char)(c)] & (_UP)); +} +static always_inline bool islower(int c) +{ + return (_ctype[(unsigned char)(c)] & (_LO)); +} +static always_inline bool isprint(int c) +{ + return (_ctype[(unsigned char)(c)] & (_LO | _UP | _DI | + _SP | _PU)); +} +static always_inline bool isalpha(int c) +{ + return (_ctype[(unsigned char)(c)] & (_LO | _UP)); +} +static always_inline bool iscntrl(int c) +{ + return (_ctype[(unsigned char)(c)] & (_CN)); +} + + +#endif /* __CTYPE_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/efibase.h b/tboot/include/efibase.h new file mode 100644 index 0000000..7138b79 --- /dev/null +++ b/tboot/include/efibase.h @@ -0,0 +1,46 @@ +/* + * efibase.h: EFI base includes. + * + * Copyright (c) 2017 Assured Information Security. + * + * Ross Philipson + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef __EFIBASE_H__ +#define __EFIBASE_H__ + +#include +#include +#include + +#include +#include + +#endif /* __EFIBASE_H__ */ diff --git a/tboot/include/eficonfig.h b/tboot/include/eficonfig.h new file mode 100644 index 0000000..fc2cf16 --- /dev/null +++ b/tboot/include/eficonfig.h @@ -0,0 +1,109 @@ +/* + * eficonfig.h: EFI related config definitions. + * + * Copyright (c) 2017 Assured Information Security. + * + * Ross Philipson + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef __EFI_CONFIG_H__ +#define __EFI_CONFIG_H__ + +#define EFI_MAX_PATH 512 +#define EFI_MAX_CONFIG_FILE 1024 /* plenty of room for a config file */ + +/* TBOOT config */ +#define SECTION_TBOOT "tboot" +# define ITEM_OPTIONS "options" +# define ITEM_XENPATH "xenpath" +# define ITEM_LCP "lcp" +#define SECTION_ACM "acm" +#define SECTION_RACM "racm" + +/* Xen config */ +#define SECTION_GLOBAL "global" +# define ITEM_DEFAULT "default" +# define ITEM_KERNEL "kernel" + +enum { + EFI_CONFIG_TBOOT = 0, + EFI_CONFIG_TBOOT_PARSED, + EFI_CONFIG_XEN, + EFI_CONFIG_XEN_PARSED, + EFI_CONFIG_MAX +}; + +typedef struct { + union { + char *buffer; + EFI_PHYSICAL_ADDRESS addr; + } u; + uint64_t size; +} efi_file_t; + +wchar_t g_tboot_dir[EFI_MAX_PATH]; +bool g_post_ebs; +const char *g_kernel_cmdline; + +/* Locations of runtime offsets */ +void *g_rtmem_base; +void *g_image_base; +uint64_t g_image_size; +void *g_text_base; +uint64_t g_text_size; +void *g_bss_base; +uint64_t g_bss_size; + +void efi_cfg_init(void); +efi_file_t *efi_get_configs(void); +void efi_cfg_pre_parse(efi_file_t *config); +char *efi_cfg_get_value(int index, const char *section, + const char *item); + +bool efi_split_kernel_line(void); +bool efi_cfg_copy_tboot_path(const wchar_t *file_path); + +const efi_file_t *efi_get_platform_sinit(void); +const efi_file_t *efi_get_platform_racm(void); +const efi_file_t *efi_get_lcp(void); +void efi_store_files(const efi_file_t *platform_sinit, + const efi_file_t *platform_racm, + const efi_file_t *lcp); + +const efi_file_t *efi_get_xen(void); +const efi_file_t *efi_get_kernel(void); +const efi_file_t *efi_get_ramdisk(void); +const void *efi_get_memory_map(uint64_t *size_out, uint64_t *size_desc_out); +uint64_t efi_get_xen_post_launch_cb(void); + +void efi_store_xen_info(void *base, uint64_t size); +bool efi_store_xen_tboot_data(efi_xen_tboot_data_t *xtd); + +#endif /* __EFI_CONFIG_H__ */ diff --git a/tboot/include/eficore.h b/tboot/include/eficore.h new file mode 100644 index 0000000..bea8694 --- /dev/null +++ b/tboot/include/eficore.h @@ -0,0 +1,134 @@ +/* + * eficore.h: EFI core support definitions. + * + * Copyright (c) 2017 Assured Information Security. + * + * Ross Philipson + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef __EFICORE_H__ +#define __EFICORE_H__ + +#define EFI_EARLY_PRINTK + +/* TODO debug only stuffs */ +#define EFI_DEBUG + +/* Shared RT variable between TBOOT and Xen */ +#define EFI_TBOOT_XEN_GUID \ + { 0xf112e6cb, 0xce01, 0x4573, {0xa0, 0x52, 0xfb, 0xdb, 0x6c, 0xc0, 0xc7, 0xcb} } + +#define EFI_TBOOT_XEN_REV 1 +#define EFI_TBOOT_XEN_NAME L"TbootXenVar" + +/* Un-extern these that are defined in the GNU-EFI headers */ +EFI_SYSTEM_TABLE *ST; +EFI_BOOT_SERVICES *BS; +EFI_RUNTIME_SERVICES *RT; + +EFI_GUID EfiGlobalVariable; +EFI_GUID NullGuid; +EFI_GUID UnknownDevice; +EFI_GUID DevicePathProtocol; +EFI_GUID LoadedImageProtocol; +EFI_GUID FileSystemProtocol; +EFI_GUID GenericFileInfo; +EFI_GUID AcpiTableGuid; +EFI_GUID Acpi20TableGuid; +EFI_GUID SMBIOSTableGuid; +EFI_GUID TbootXenGuid; + +typedef void (*post_launch_t)(void *ets); + +typedef struct __packed efi_xen_tboot_data { + void *kernel; + uint64_t kernel_size; + void *ramdisk; + uint64_t ramdisk_size; + void *memory_map; + uint64_t memory_map_size; + uint64_t memory_desc_size; + uint64_t post_launch_cb; +} efi_xen_tboot_data_t; + +typedef void (*begin_launch_t)(efi_xen_tboot_data_t *xtd); + +typedef struct __packed efi_tboot_xen_var { + uint64_t revision; + const char *xen_config; + uint64_t xen_config_size; + uint64_t begin_launch_cb; +} efi_tboot_xen_var_t; + +/* The following routines are available before and after EBS */ + +void atow(wchar_t *dst, const char *src, uint64_t count); +bool wtoa(char *dst, const wchar_t *src, uint64_t count); +uint64_t wcslen(const wchar_t *str); + +uint8_t *efi_get_rsdp(void); + +void *efi_get_pe_section(const char *name, void *image_base, + uint64_t *size_out); + +void efi_shutdown_system(uint32_t shutdown_type); + +/* The following routines are only available after EBS */ + +bool efi_scan_memory_map(void); +bool efi_add_resmap_entry(uint64_t addr, uint64_t length); +bool efi_get_ram_ranges(uint64_t *min_lo_ram, uint64_t *max_lo_ram, + uint64_t *min_hi_ram, uint64_t *max_hi_ram); + +/* The following routines are unavailable after EBS */ + +wchar_t *atow_alloc(const char *src); +char *wtoa_alloc(const wchar_t *src); + +wchar_t *atow_cat(const wchar_t *base, const char *tail); + +void efi_puts(const char *s, unsigned int count); + +EFI_DEVICE_PATH *efi_get_device_path(const wchar_t *path, + EFI_HANDLE parent); +EFI_STATUS efi_device_path_to_text(EFI_DEVICE_PATH *dev_path, + wchar_t *path_out, + uint64_t count); +EFI_FILE_INFO *efi_get_file_info(EFI_FILE *target_file, + EFI_MEMORY_TYPE mem_type); +EFI_STATUS efi_read_file(EFI_FILE_IO_INTERFACE *file_system, + wchar_t *file_name, + EFI_MEMORY_TYPE mem_type, + uint64_t *size_out, + EFI_PHYSICAL_ADDRESS *addr_out); + +void efi_launch_kernel(void); + +#endif /* __EFICORE_H__ */ diff --git a/tboot/include/hash.h b/tboot/include/hash.h new file mode 100644 index 0000000..9d961e7 --- /dev/null +++ b/tboot/include/hash.h @@ -0,0 +1,123 @@ +/* + * hash.h: definition of and support fns for tb_hash_t type + * + * Copyright (c) 2006-2007, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __HASH_H__ +#define __HASH_H__ + +#define TB_HALG_SHA1_LG 0x0000 /* legacy define for SHA1 */ +#define TB_HALG_SHA1 0x0004 +#define TB_HALG_SHA256 0x000B +#define TB_HALG_SM3 0x0012 +#define TB_HALG_SHA384 0x000C +#define TB_HALG_SHA512 0x000D +#define TB_HALG_NULL 0x0010 + +#define SHA1_LENGTH 20 +#define SHA256_LENGTH 32 +#define SM3_LENGTH 32 +#define SHA384_LENGTH 48 +#define SHA512_LENGTH 64 + +typedef uint8_t sha1_hash_t[SHA1_LENGTH]; +typedef uint8_t sha256_hash_t[SHA256_LENGTH]; +typedef uint8_t sm3_hash_t[SM3_LENGTH]; +typedef uint8_t sha384_hash_t[SHA384_LENGTH]; +typedef uint8_t sha512_hash_t[SHA512_LENGTH]; + +typedef union { + uint8_t sha1[SHA1_LENGTH]; + uint8_t sha256[SHA256_LENGTH]; + uint8_t sm3[SM3_LENGTH]; + uint8_t sha384[SHA384_LENGTH]; +} tb_hash_t; + +static inline const char *hash_alg_to_string(uint16_t hash_alg) +{ + if ( hash_alg == TB_HALG_SHA1 || hash_alg == TB_HALG_SHA1_LG ) + return "TB_HALG_SHA1"; + else if ( hash_alg == TB_HALG_SHA256 ) + return "TB_HALG_SHA256"; + else if ( hash_alg == TB_HALG_SM3 ) + return "TB_HALG_SM3"; + else if ( hash_alg == TB_HALG_SHA384 ) + return "TB_HALG_SHA384"; + else if ( hash_alg == TB_HALG_SHA512 ) + return "TB_HALG_SHA512"; + else { + static char buf[32]; + snprintf(buf, sizeof(buf), "unsupported (%u)", hash_alg); + return buf; + } +} + +static inline unsigned int get_hash_size(uint16_t hash_alg) +{ + if ( hash_alg == TB_HALG_SHA1 || hash_alg == TB_HALG_SHA1_LG ) + return SHA1_LENGTH; + else if ( hash_alg == TB_HALG_SHA256 ) + return SHA256_LENGTH; + else if ( hash_alg == TB_HALG_SM3 ) + return SM3_LENGTH; + else if ( hash_alg == TB_HALG_SHA384 ) + return SHA384_LENGTH; + else if ( hash_alg == TB_HALG_SHA512 ) + return SHA512_LENGTH; + else + return 0; +} + +bool are_hashes_equal(const tb_hash_t *hash1, const tb_hash_t *hash2, + uint16_t hash_alg); +bool hash_buffer(const unsigned char* buf, size_t size, tb_hash_t *hash, + uint16_t hash_alg); +bool extend_hash(tb_hash_t *hash1, const tb_hash_t *hash2, + uint16_t hash_alg); +void print_hash(const tb_hash_t *hash, uint16_t hash_alg); +void copy_hash(tb_hash_t *dest_hash, const tb_hash_t *src_hash, + uint16_t hash_alg); + + +#endif /* __HASH_H__ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/integrity.h b/tboot/include/integrity.h new file mode 100644 index 0000000..1051e71 --- /dev/null +++ b/tboot/include/integrity.h @@ -0,0 +1,106 @@ +/* + * integrity.h: routines for memory integrity measurement & + * verification. Memory integrity is protected with tpm seal + * + * Copyright (c) 2007-2009, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef _TBOOT_INTEGRITY_H_ +#define _TBOOT_INTEGRITY_H_ + +#include +#include + +/* + * state that must be saved across S3 and will be sealed for integrity + * before extending PCRs and launching kernel + */ +#define MAX_VL_HASHES 32 +#define MAX_ALG_NUM 5 + +typedef struct { + uint16_t alg; + tb_hash_t hash; +} hash_entry_t; + +typedef struct { + uint32_t count; + hash_entry_t entries[MAX_ALG_NUM]; +} hash_list_t; + +typedef struct { + /* low and high memory regions to protect w/ VT-d PMRs */ + uint64_t vtd_pmr_lo_base; + uint64_t vtd_pmr_lo_size; + uint64_t vtd_pmr_hi_base; + uint64_t vtd_pmr_hi_size; + /* VL policy at time of sealing */ + tb_hash_t pol_hash; + /* verified launch measurements to be re-extended in DRTM PCRs + * a given PCR may have more than one hash and will get extended in the + * order it appears in the list */ + uint8_t num_vl_entries; + struct { + uint8_t pcr; + hash_list_t hl; + } vl_entries[MAX_VL_HASHES]; +} pre_k_s3_state_t; + +/* + * state that must be saved across S3 and will be sealed for integrity + * just before entering S3 (after kernel shuts down) + */ +typedef struct { + uint64_t kernel_s3_resume_vector; + vmac_t kernel_integ; +} post_k_s3_state_t; + + +pre_k_s3_state_t g_pre_k_s3_state; +post_k_s3_state_t g_post_k_s3_state; + +bool seal_pre_k_state(void); +bool seal_post_k_state(void); +bool verify_integrity(void); + +#endif /* _TBOOT_INTEGRITY_H_ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/io.h b/tboot/include/io.h new file mode 100644 index 0000000..71ef0ad --- /dev/null +++ b/tboot/include/io.h @@ -0,0 +1,91 @@ +/*- + * Copyright (c) 1993 The Regents of the University of California. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 4. Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ +/* + * Portions copyright (c) 2010, Intel Corporation + */ + +#ifndef __IO_H__ +#define __IO_H__ + +/* from: + * $FreeBSD: src/sys/i386/include/cpufunc.h,v 1.158 2010/01/01 20:55:11 obrien Exp $ + */ + +/* modified to use tboot's types */ + +#define readb(va) (*(volatile uint8_t *) (va)) +#define readw(va) (*(volatile uint16_t *) (va)) +#define readl(va) (*(volatile uint32_t *) (va)) + +#define writeb(va, d) (*(volatile uint8_t *) (va) = (d)) +#define writew(va, d) (*(volatile uint16_t *) (va) = (d)) +#define writel(va, d) (*(volatile uint32_t *) (va) = (d)) + +static inline uint8_t inb(uint16_t port) +{ + uint8_t data; + + __asm volatile("inb %w1, %0" : "=a" (data) : "Nd" (port)); + return (data); +} + +static inline uint16_t inw(uint16_t port) +{ + uint16_t data; + + __asm volatile("inw %w1, %0" : "=a" (data) : "Nd" (port)); + return (data); +} + +static inline uint32_t inl(uint16_t port) +{ + uint32_t data; + + __asm volatile("inl %w1, %0" : "=a" (data) : "Nd" (port)); + return (data); +} + +static inline void outb(uint16_t port, uint8_t data) +{ + __asm __volatile("outb %0, %w1" : : "a" (data), "Nd" (port)); +} + +static inline void outw(uint16_t port, uint16_t data) +{ + __asm volatile("outw %0, %w1" : : "a" (data), "Nd" (port)); +} + +static inline void outl(uint16_t port, uint32_t data) +{ + __asm volatile("outl %0, %w1" : : "a" (data), "Nd" (port)); +} + + +#endif /* __IO_H__ */ diff --git a/tboot/include/lcp3.h b/tboot/include/lcp3.h new file mode 100644 index 0000000..4c717fe --- /dev/null +++ b/tboot/include/lcp3.h @@ -0,0 +1,282 @@ +/* + * Copyright 2014 Intel Corporation. All Rights Reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * Neither the name Intel Corporation nor the names of its contributors may be + * used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef __LCP_H__ +#define __LCP_H__ + +#ifndef __packed +#define __packed __attribute__ ((packed)) +#endif + +/* + * Version = 3.0 - new version format of LCP Policy. Major version + * is incremented since layout is incompatible with previous revision. + */ + +/*--------- LCP UUID ------------*/ +#define LCP_POLICY_DATA_UUID {0xab0d1925, 0xeee7, 0x48eb, 0xa9fc, \ + {0xb, 0xac, 0x5a, 0x26, 0x2d, 0xe}} + +/*--------- CUSTOM ELT UUID ------------*/ +#define LCP_CUSTOM_ELEMENT_TBOOT_UUID {0xc3930641, 0xe3cb, 0x4f40, 0x91d7, \ + {0x27, 0xf8, 0xb9, 0xe2, 0x5c, 0x86}} + +/*--------- LCP FILE SIGNATURE ------------*/ +#define LCP_POLICY_DATA_FILE_SIGNATURE "Intel(R) TXT LCP_POLICY_DATA\0\0\0\0" + +/*--------- LCP Policy Type ------------*/ +#define LCP_POLTYPE_LIST 0 +#define LCP_POLTYPE_ANY 1 + + +#define LCP_DEFAULT_POLICY_VERSION 0x0300 +#define LCP_DEFAULT_POLICY_CONTROL 0x00 + +#define LCP_MAX_LISTS 8 + + +/*--------- with LCP_POLICY version 2.0 ------------*/ +#define SHA1_LENGTH 20 +#define SHA256_LENGTH 32 + +typedef union { + uint8_t sha1[SHA1_LENGTH]; + uint8_t sha256[SHA256_LENGTH]; +} lcp_hash_t; + +#define LCP_POLSALG_NONE 0 +#define LCP_POLSALG_RSA_PKCS_15 1 + +#define LCP_SIG_EXPONENT 65537 + +typedef struct __packed { + uint16_t revocation_counter; + uint16_t pubkey_size; + uint8_t pubkey_value[0]; + uint8_t sig_block[]; +} lcp_signature_t; + +/* set bit 0: override PS policy for this element type */ +#define DEFAULT_POL_ELT_CONTROL 0x0001 +typedef struct __packed { + uint32_t size; + uint32_t type; + uint32_t policy_elt_control; + uint8_t data[]; +} lcp_policy_element_t; + +#define LCP_POLELT_TYPE_CUSTOM 3 +typedef struct __packed { + uuid_t uuid; + uint8_t data[]; +} lcp_custom_element_t; + +#define LCP_DEFAULT_POLICY_LIST_VERSION 0x0200 +#define LCP_TPM12_POLICY_LIST_VERSION 0x0100 +#define LCP_TPM20_POLICY_LIST_VERSION 0x0200 +typedef struct __packed { + uint16_t version; /* = 1.0 */ + uint8_t reserved; + uint8_t sig_alg; + uint32_t policy_elements_size; + lcp_policy_element_t policy_elements[]; + /* optionally: */ + /* lcp_signature_t sig; */ +} lcp_policy_list_t; + +#define LCP_FILE_SIG_LENGTH 32 +typedef struct __packed { + char file_signature[LCP_FILE_SIG_LENGTH]; + uint8_t reserved[3]; + uint8_t num_lists; + lcp_policy_list_t policy_lists[]; +} lcp_policy_data_t; + +#define LCP_DEFAULT_POLICY_VERSION_2 0x0202 +typedef struct __packed { + uint16_t version; + uint8_t hash_alg; /* one of LCP_POLHALG_* */ + uint8_t policy_type; /* one of LCP_POLTYPE_* */ + uint8_t sinit_min_version; + uint8_t reserved1; + uint16_t data_revocation_counters[LCP_MAX_LISTS]; + uint32_t policy_control; + uint32_t reserved2[2]; + lcp_hash_t policy_hash; +} lcp_policy_t; + + +/*--------- LCP_POLICY version 3.0 ------------*/ +#define TPM_ALG_SHA1 0x0004 +#define TPM_ALG_SHA256 0x000B +#define TPM_ALG_SHA384 0x000C +#define TPM_ALG_SHA512 0x000D +#define TPM_ALG_NULL 0x0010 +#define TPM_ALG_SM3_256 0x0012 + +#define TPM_ALG_RSASSA 0x0014 +#define TPM_ALG_ECDSA 0x0018 +#define TPM_ALG_SM2 0x001B + +#define SHA1_DIGEST_SIZE 20 +#define SHA256_DIGEST_SIZE 32 +#define SHA384_DIGEST_SIZE 48 +#define SHA512_DIGEST_SIZE 64 +#define SM3_256_DIGEST_SIZE 32 + +typedef union { + uint8_t sha1[SHA1_DIGEST_SIZE]; + uint8_t sha256[SHA256_DIGEST_SIZE]; + uint8_t sha384[SHA384_DIGEST_SIZE]; + uint8_t sha512[SHA512_DIGEST_SIZE]; + uint8_t sm3[SM3_256_DIGEST_SIZE]; +} lcp_hash_t2; + +typedef struct __packed { + uint16_t hash_alg; + uint8_t size_of_select; + uint8_t pcr_select[]; +} tpms_pcr_selection_t; + +typedef struct __packed { + uint32_t count; + tpms_pcr_selection_t pcr_selections; +} tpml_pcr_selection_t; + +typedef struct __packed { + uint16_t size; + uint8_t buffer[]; +} tpm2b_digest_t; + +typedef struct __packed { + tpml_pcr_selection_t pcr_selection; + tpm2b_digest_t pcr_digest; +} tpms_quote_info_t; + +#define LCP_POLELT_TYPE_MLE2 0x10 +typedef struct __packed { + uint8_t sinit_min_version; + uint8_t reserved; + uint16_t hash_alg; + uint16_t num_hashes; + lcp_hash_t2 hashes[]; +} lcp_mle_element_t2; + +#define LCP_POLELT_TYPE_PCONF2 0x11 +typedef struct __packed { + uint16_t hash_alg; + uint16_t num_pcr_infos; + tpms_quote_info_t prc_infos[]; +} lcp_pconf_element_t2; + +#define LCP_POLELT_TYPE_SBIOS2 0x12 +typedef struct __packed { + uint16_t hash_alg; + uint8_t reserved1[2]; + lcp_hash_t2 fallback_hash; + uint16_t reserved2; + uint16_t num_hashes; + lcp_hash_t2 hashes[]; +} lcp_sbios_element_t2; + +#define LCP_POLELT_TYPE_CUSTOM2 0x13 +typedef struct __packed { + uuid_t uuid; + uint8_t data[]; +} lcp_custom_element_t2; + +#define LCP_POLELT_TYPE_STM2 0x14 +typedef struct __packed { + uint16_t hash_alg; + uint16_t num_hashes; + lcp_hash_t2 hashes[]; +} lcp_stm_element_t2; + +typedef struct __packed { + uint16_t version; /* = 3.0 */ + uint16_t hash_alg; /* one of LCP_POLHALG_* */ + uint8_t policy_type; /* one of LCP_POLTYPE_* */ + uint8_t sinit_min_version; + uint16_t data_revocation_counters[LCP_MAX_LISTS]; + uint32_t policy_control; + uint8_t max_sinit_min_ver; /* Defined for PO only. Reserved for PS */ + uint8_t max_biosac_min_ver; /* Defined for PO only. Reserved for PS */ + uint16_t lcp_hash_alg_mask; /* Mask of approved algorithms for LCP evaluation */ + uint32_t lcp_sign_alg_mask; /* Mask of approved signature algorithms for LCP evaluation */ + uint16_t aux_hash_alg_mask; /* Approved algorithm for auto - promotion hash */ + uint16_t reserved2; + lcp_hash_t2 policy_hash; +} lcp_policy_t2; + +typedef struct __packed { + uint16_t revocation_counter; + uint16_t pubkey_size; + uint8_t pubkey_value[0]; + uint8_t sig_block[]; +} lcp_rsa_signature_t; + +typedef struct __packed { + uint16_t revocation_counter; + uint16_t pubkey_size; + uint32_t reserved; + uint8_t qx[0]; + uint8_t qy[0]; + uint8_t r[0]; + uint8_t s[0]; +} lcp_ecc_signature_t; + +typedef union __packed { + lcp_rsa_signature_t rsa_signature; + lcp_ecc_signature_t ecc_signature; +} lcp_signature_t2; + +typedef struct __packed { + uint16_t version; /* = 2.0 */ + uint16_t sig_alg; + uint32_t policy_elements_size; + lcp_policy_element_t policy_elements[]; +//#if (sig_alg != TPM_ALG_NULL) +// lcp_signature_t sig; +//#endif +} lcp_policy_list_t2; + +typedef union __packed { + lcp_policy_list_t tpm12_policy_list; + lcp_policy_list_t2 tpm20_policy_list; +} lcp_list_t; + +typedef struct __packed { + char file_signature[32]; + uint8_t reserved[3]; + uint8_t num_lists; + lcp_list_t policy_lists[]; +} lcp_policy_data_t2; + +#endif /* __LCP_H__ */ diff --git a/tboot/include/lcp3_hlp.h b/tboot/include/lcp3_hlp.h new file mode 100644 index 0000000..92061e4 --- /dev/null +++ b/tboot/include/lcp3_hlp.h @@ -0,0 +1,117 @@ +/* + * Copyright 2014 Intel Corporation. All Rights Reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * Redistributions of source code must retain the above copyright notice, this + * list of conditions and the following disclaimer. + * + * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * Neither the name Intel Corporation nor the names of its contributors may be + * used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef __TXT_LCP2_HELPER_H__ +#define __TXT_LCP2_HELPER_H__ + +static inline lcp_signature_t *get_tpm12_signature(const lcp_policy_list_t *pollist) +{ + if ( pollist == NULL ) + return NULL; + + if ( pollist->sig_alg != LCP_POLSALG_RSA_PKCS_15 ) + return NULL; + + return (lcp_signature_t *)((const void *)&pollist->policy_elements + + pollist->policy_elements_size); +} + +static inline size_t get_tpm12_signature_size(const lcp_signature_t *sig) +{ + if ( sig == NULL ) + return 0; + + return offsetof(lcp_signature_t, pubkey_value) + 2*sig->pubkey_size; +} + +static inline size_t get_tpm12_policy_list_size(const lcp_policy_list_t *pollist) +{ + size_t size = 0; + + if ( pollist == NULL ) + return 0; + + size = offsetof(lcp_policy_list_t, policy_elements) + + pollist->policy_elements_size; + + /* add sig size */ + if ( pollist->sig_alg == LCP_POLSALG_RSA_PKCS_15 ) + size += get_tpm12_signature_size(get_tpm12_signature(pollist)); + + return size; +} + +static inline lcp_signature_t2 *get_tpm20_signature(const lcp_policy_list_t2 *pollist) +{ + if ( pollist == NULL || pollist->sig_alg == TPM_ALG_NULL ) + return NULL; + + return (lcp_signature_t2 *)((const void *)&pollist->policy_elements + + pollist->policy_elements_size); +} + +static inline size_t get_tpm20_signature_size(const lcp_signature_t2 *sig, + const uint16_t sig_alg) +{ + if ( sig == NULL ) + return 0; + + if ( sig_alg == TPM_ALG_RSASSA) + return offsetof(lcp_rsa_signature_t, pubkey_value) + + 2*sig->rsa_signature.pubkey_size; + else if ( sig_alg == TPM_ALG_ECDSA) + return offsetof(lcp_ecc_signature_t, qx) + + 2*sig->ecc_signature.pubkey_size; + + return 0; +} + +static inline size_t get_tpm20_policy_list_size(const lcp_policy_list_t2 *pollist) +{ + size_t size = 0; + + if ( pollist == NULL ) + return 0; + + size = offsetof(lcp_policy_list_t2, policy_elements) + + pollist->policy_elements_size; + + /* add sig size */ + if ( pollist->sig_alg == TPM_ALG_RSASSA || + pollist->sig_alg == TPM_ALG_ECDSA || + pollist->sig_alg == TPM_ALG_SM2 ) + size += get_tpm20_signature_size(get_tpm20_signature(pollist), + pollist->sig_alg); + + return size; +} + + +#endif /* __TXT_LCP3_HELPER_H__ */ diff --git a/tboot/include/misc.h b/tboot/include/misc.h new file mode 100644 index 0000000..6c118c0 --- /dev/null +++ b/tboot/include/misc.h @@ -0,0 +1,95 @@ +/* + * misc.h: miscellaneous support fns + * + * Copyright (c) 2010, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __MISC_H__ +#define __MISC_H__ + +void print_hex(const char * buf, const void * prtptr, size_t size); + +void print_system_values(void); + +void print_test_chars(void); + +bool test_virt_to_phys(uint64_t vaddr); +void dump_page_tables(void); + +void delay(int millisecs); + +/* + * These three "plus overflow" functions take a "x" value + * and add the "y" value to it and if the two values are + * greater than the size of the variable type, they will + * overflow the type and end up with a smaller value and + * return TRUE - that they did overflow. i.e. + * x + y <= variable type maximum. + */ +static inline bool plus_overflow_u64(uint64_t x, uint64_t y) +{ + return ((((uint64_t)(~0)) - x) < y); +} + +static inline bool plus_overflow_u32(uint32_t x, uint32_t y) +{ + return ((((uint32_t)(~0)) - x) < y); +} + +/* + * This checks to see if two numbers multiplied together are larger + * than the type that they are. Returns TRUE if OVERFLOWING. + * If the first parameter "x" is greater than zero and + * if that is true, that the largest possible value 0xFFFFFFFF / "x" + * is less than the second parameter "y". If "y" is zero then + * it will also fail because no unsigned number is less than zero. + */ +static inline bool multiply_overflow_u32(uint32_t x, uint32_t y) +{ + return (x > 0) ? ((((uint32_t)(~0))/x) < y) : false; +} + +#define ARRAY_SIZE(a) (sizeof(a) / sizeof(a[0])) + +#define AP_WAKE_TRIGGER_DEF 0xffffffff + +#endif /* __MISC_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/mle.h b/tboot/include/mle.h new file mode 100644 index 0000000..c0d7386 --- /dev/null +++ b/tboot/include/mle.h @@ -0,0 +1,96 @@ +/* + * mle.h: Intel(r) TXT MLE header definition + * + * Copyright (c) 2003-2008, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __MLE_H__ +#define __MLE_H__ + +/* + * SINIT/MLE capabilities + */ +typedef union { + uint32_t _raw; + struct { + uint32_t rlp_wake_getsec : 1; + uint32_t rlp_wake_monitor : 1; + uint32_t ecx_pgtbl : 1; + uint32_t stm : 1; + uint32_t pcr_map_no_legacy : 1; + uint32_t pcr_map_da : 1; + uint32_t platform_type : 2; + uint32_t max_phy_addr : 1; + uint32_t reserved1 : 23; + }; +} txt_caps_t; + + +/* + * MLE header structure + * describes an MLE for SINIT and OS/loader SW + */ +typedef struct { + uuid_t uuid; + uint32_t length; + uint32_t version; + uint32_t entry_point; + uint32_t first_valid_page; + uint32_t mle_start_off; + uint32_t mle_end_off; + txt_caps_t capabilities; + uint32_t cmdline_start_off; + uint32_t cmdline_end_off; +} mle_hdr_t; + +#define MLE_HDR_UUID {0x9082ac5a, 0x476f, 0x74a7, 0x5c0f, \ + {0x55, 0xa2, 0xcb, 0x51, 0xb6, 0x42}} + +/* + * values supported by current version of tboot + */ +#define MLE_HDR_VER 0x00020001 /* 2.1 */ +#define MLE_HDR_CAPS 0x00000027 /* rlp_wake_{getsec, monitor} = 1, + ecx_pgtbl = 1, nolg = 0, da = 1 */ + +#endif /* __MLE_H__ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/msr.h b/tboot/include/msr.h new file mode 100644 index 0000000..70f1a32 --- /dev/null +++ b/tboot/include/msr.h @@ -0,0 +1,90 @@ +/*- + * Copyright (c) 1993 The Regents of the University of California. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 4. Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ +/* + * Portions copyright (c) 2010-2011, Intel Corporation + */ + + +#ifndef __MSR_H__ +#define __MSR_H__ + +/* N.B. see processor.h, rd/wrmsr got moved and are not implemented as inline + * asm any longer. + */ + +/* + * from: @(#)specialreg.h 7.1 (Berkeley) 5/9/91 + * $FreeBSD: src/sys/i386/include/specialreg.h,v 1.53.2.1.2.2 2009/11/06 17:09:04 attilio Exp $ + */ + +#define MSR_IA32_PLATFORM_ID 0x017 +#define MSR_APICBASE 0x01b +#define MSR_IA32_FEATURE_CONTROL 0x03a +#define MSR_IA32_SMM_MONITOR_CTL 0x09b +#define MSR_MTRRcap 0x0fe +#define MSR_MCG_CAP 0x179 +#define MSR_MCG_STATUS 0x17a +#define MSR_IA32_MISC_ENABLE 0x1a0 +#define MSR_IA32_MISC_ENABLE_MONITOR_FSM (1<<18) +#define MSR_MTRRdefType 0x2ff +#define MSR_MC0_STATUS 0x401 +#define MSR_IA32_VMX_BASIC_MSR 0x480 +#define MSR_IA32_VMX_PINBASED_CTLS_MSR 0x481 +#define MSR_IA32_VMX_PROCBASED_CTLS_MSR 0x482 +#define MSR_IA32_VMX_EXIT_CTLS_MSR 0x483 +#define MSR_IA32_VMX_ENTRY_CTLS_MSR 0x484 +#define MSR_IA32_SE_SVN_STATUS 0x500 +/* + * Constants related to MSR's. + */ +#define APICBASE_BSP 0x00000100 + +#define MSR_IA32_SMM_MONITOR_CTL_VALID 1 +#define MSR_IA32_SMM_MONITOR_CTL_MSEG_BASE(x) (x>>12) + +/* MSRs & bits used for VMX enabling */ +#define IA32_FEATURE_CONTROL_MSR_LOCK 0x1 +#define IA32_FEATURE_CONTROL_MSR_ENABLE_VMX_IN_SMX 0x2 +#define IA32_FEATURE_CONTROL_MSR_SENTER_PARAM_CTL 0x7f00 +#define IA32_FEATURE_CONTROL_MSR_ENABLE_SENTER 0x8000 + +/* AMD64 MSR's */ +#define MSR_EFER 0xc0000080 /* extended features */ + +/* EFER bits */ +#define _EFER_LME 8 /* Long mode enable */ +#define _EFER_LMA 10 /* Long mode active */ + +#define MTRR_TYPE_UNCACHABLE 0 +#define MTRR_TYPE_WRTHROUGH 4 +#define MTRR_TYPE_WRBACK 6 + + +#endif /* __MSR_H__ */ diff --git a/tboot/include/mutex.h b/tboot/include/mutex.h new file mode 100644 index 0000000..d61bd99 --- /dev/null +++ b/tboot/include/mutex.h @@ -0,0 +1,58 @@ +/* $OpenBSD: mutex.h,v 1.6 2009/04/27 21:48:56 kettenis Exp $ */ +/* + * Copyright (c) 2004 Artur Grabowski + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. The name of the author may not be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, + * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY + * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL + * THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; + * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, + * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR + * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF + * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ +/* + * Portions copyright (c) 2010, Intel Corporation + */ + +#ifndef __MUTEX_H__ +#define __MUTEX_H__ + +/* + * A mutex is: + * - owned by a cpu. + * - non-recursive. + * - spinning. + * - not providing mutual exclusion between processes, only cpus. + * - providing interrupt blocking when necessary. + * + * Different mutexes can be nested, but not interleaved. This is ok: + * "mtx_enter(foo); mtx_enter(bar); mtx_leave(bar); mtx_leave(foo);" + * This is _not_ ok: + * "mtx_enter(foo); mtx_enter(bar); mtx_leave(foo); mtx_leave(bar);" + */ + +struct mutex { + __volatile__ uint64_t mtx_lock; +}; + +/* + * Some architectures need to do magic for the ipl, so they need a macro. + */ +void mtx_init(struct mutex *); +void mtx_enter(struct mutex *); +void mtx_leave(struct mutex *); + +#endif /* __MUTEX_H__ */ diff --git a/tboot/include/page.h b/tboot/include/page.h new file mode 100644 index 0000000..b0588f6 --- /dev/null +++ b/tboot/include/page.h @@ -0,0 +1,66 @@ +/* + * page.h: definitions for page size/mask/shift/etc. + * + * Copyright (c) 2010, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __PAGE_H__ +#define __PAGE_H__ + +/* From http://fxr.watson.org/fxr/source/i386/include/param.h */ +#define PAGE_SHIFT 12 /* LOG2(PAGE_SIZE) */ +#define PAGE_SIZE (1 << PAGE_SHIFT) /* bytes/page */ +/* PAGE_MASK is used to pass bits 12 and above. */ +#define PAGE_MASK (~(PAGE_SIZE-1)) + +/* This is used to address the L2's 4MB pages */ +/* From figure 4-3 of IA64/IA32 Arch SDM vol 3A */ +#define FOURMB_PAGE_SHIFT 22 + +/* macros to rounds things up/down to a page/pfn */ +#define PAGE_UP(p) (((unsigned long long)(p) + PAGE_SIZE- 1) & PAGE_MASK) +#define PAGE_DOWN(p) ((unsigned long long)(p) & PAGE_MASK) +#define PFN_DOWN(x) ((x) >> PAGE_SHIFT) +#define PFN_UP(x) (((x) + PAGE_SIZE-1) >> PAGE_SHIFT) + +#endif /* __PAGE_H__ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/paging.h b/tboot/include/paging.h new file mode 100644 index 0000000..7896824 --- /dev/null +++ b/tboot/include/paging.h @@ -0,0 +1,122 @@ +/* + * paging.h: Definitions for paging in tboot (PAE+PSE) + * + * Copyright (c) 2006-2010, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __PAGING_H__ +#define __PAGING_H__ + +/* direct map starts from 0, size 64M */ +#define DIRECTMAP_VIRT_START 0 +#define DIRECTMAP_VIRT_ORDER 26 +#define DIRECTMAP_VIRT_SIZE (1UL << DIRECTMAP_VIRT_ORDER) +#define DIRECTMAP_VIRT_END (DIRECTMAP_VIRT_START + DIRECTMAP_VIRT_SIZE) + +/* MAC window starts from 0x80000000, size 1G */ +#define MAC_VIRT_START 0x80000000 +#define MAC_VIRT_ORDER 30 +#define MAC_VIRT_SIZE (1UL << MAC_VIRT_ORDER) +#define MAC_VIRT_END (MAC_VIRT_START + MAC_VIRT_SIZE) + +/* PAE with 2-Mbyte Pages */ +#define TB_PAGETABLE_ORDER 9 +#define TB_L1_PAGETABLE_ENTRIES (1 << TB_PAGETABLE_ORDER) +#define TB_L2_PAGETABLE_ENTRIES (1 << TB_PAGETABLE_ORDER) + +#define TB_L1_PAGETABLE_SHIFT 21 +#define TB_L2_PAGETABLE_SHIFT 30 + +#define MAC_PAGE_SIZE (1UL << TB_L1_PAGETABLE_SHIFT) +#define MAC_PAGE_MASK (~(MAC_PAGE_SIZE - 1)) + +#define _PAGE_PRESENT 0x01 +#define _PAGE_RW 0x02 +#define _PAGE_SIZE 0x80 + + +#define MAKE_TB_PDE(paddr) \ + (((uint64_t)(paddr) & ~0x00000000001FFFFF) | _PAGE_PRESENT \ + | _PAGE_RW | _PAGE_SIZE) +#define MAKE_TB_PDPTE(paddr) \ + (((uint64_t)(paddr) & ~0x0000000000000FFF) | _PAGE_PRESENT) + +/* Given a virtual address, get an entry offset into a page table. */ +#define pd_table_offset(a) \ + (((a) >> TB_L1_PAGETABLE_SHIFT) & (TB_L1_PAGETABLE_ENTRIES - 1)) +#define pdptr_table_offset(a) \ + (((a) >> TB_L2_PAGETABLE_SHIFT) & (TB_L2_PAGETABLE_ENTRIES - 1)) + +/* PAE: 52 bit physical address */ +#define PADDR_BIT 52 +#define PADDR_MASK ((1ULL << PADDR_BIT) - 1) + +/* + * PDE entry + * 31-bit pfn = pde[51:21] + * 13-bit flags = pde[12:0] + */ +#define PDE_FLAG_BIT 13 +#define PDE_FLAG_MASK ((1UL << PDE_FLAG_BIT) - 1) +#define PDE_PADDR_MASK (PADDR_MASK & (~PDE_FLAG_MASK)) +#define get_pde_flags(pde) ((int)(pde) & PDE_FLAG_MASK) +#define get_pde_paddr(pde) ((pde) & PDE_PADDR_MASK) + +/* + * PDPTE entry + * 40-bit pfn = pdptre[51:12] + * 12-bit flags = pdptre[11:0] + */ +#define PDPTE_FLAG_BIT 12 +#define PDPTE_FLAG_MASK ((1UL << PDPTE_FLAG_BIT) - 1) +#define PDPTE_PADDR_MASK (PADDR_MASK & (~PDPTE_FLAG_MASK)) +#define get_pdptre_flags(pdptre) ((int)(pdptre) & PDPTE_FLAG_MASK) +#define get_pdptre_paddr(pdptre) ((pdptre) & PDPTE_PADDR_MASK) + +void map_pages_to_tboot(unsigned long vstart, + unsigned long pfn, + unsigned long nr_pfns); +void destroy_tboot_mapping(unsigned long vstart, unsigned long vend); +bool enable_paging(void); +bool disable_paging(void); + +#endif /* __PAGING_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/pci_cfgreg.h b/tboot/include/pci_cfgreg.h new file mode 100644 index 0000000..d231e86 --- /dev/null +++ b/tboot/include/pci_cfgreg.h @@ -0,0 +1,73 @@ +/* + * Copyright (c) 1997, Stefan Esser + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice unmodified, this list of conditions, and the following + * disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * $FreeBSD: src/sys/i386/include/pci_cfgreg.h,v 1.15.2.1.4.1 2010/06/14 02:09:06 kensmith Exp $ + * $FreeBSD: src/sys/dev/pci/pcireg.h,v 1.72.2.4.2.1 2010/06/14 02:09:06 kensmith Exp $ + */ +/* + * Portions copyright (c) 2010, Intel Corporation + */ + +#ifndef __PCI_CFGREG_H__ +#define __PCI_CFGREG_H__ + +#define PCI_BUSMAX 255 /* highest supported bus number */ +#define PCI_SLOTMAX 31 /* highest supported slot number */ +#define PCI_FUNCMAX 7 /* highest supported function number */ +#define PCI_REGMAX 255 /* highest supported config register addr. */ + +#define CONF1_ADDR_PORT 0x0cf8 +#define CONF1_DATA_PORT 0x0cfc + +#define CONF1_ENABLE 0x80000000ul +#define CONF1_ENABLE_CHK 0x80000000ul +#define CONF1_ENABLE_MSK 0x7f000000ul +#define CONF1_ENABLE_CHK1 0xff000001ul +#define CONF1_ENABLE_MSK1 0x80000001ul +#define CONF1_ENABLE_RES1 0x80000000ul + +#define CONF2_ENABLE_PORT 0x0cf8 +#define CONF2_FORWARD_PORT 0x0cfa + +#define CONF2_ENABLE_CHK 0x0e +#define CONF2_ENABLE_RES 0x0e + +#define PCIR_COMMAND 0x04 +#define PCIR_BARS 0x10 +#define PCIR_IOBASEL_1 0x1c + +int pcireg_cfgread(int bus, int slot, int func, int reg, int bytes); +void pcireg_cfgwrite(int bus, int slot, int func, int reg, int data, int bytes); + +#endif /* __PCI_CFGREG_H__ */ +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/printk.h b/tboot/include/printk.h new file mode 100644 index 0000000..d72d2f2 --- /dev/null +++ b/tboot/include/printk.h @@ -0,0 +1,79 @@ +/* + * printk.h: printk to serial for very early boot stages + * + * Copyright (c) 2006-2010, Intel Corporation + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __PRINTK_H__ +#define __PRINTK_H__ + +#include +#include + +#define TBOOT_LOGBUF_SIZE 256 + +#define TBOOT_LOG_LEVEL_NONE 0x00 +#define TBOOT_LOG_LEVEL_ERR 0x01 +#define TBOOT_LOG_LEVEL_WARN 0x02 +#define TBOOT_LOG_LEVEL_INFO 0x04 +#define TBOOT_LOG_LEVEL_DETA 0x08 +#define TBOOT_LOG_LEVEL_ALL 0xFF + +#define TBOOT_LOG_TARGET_NONE 0x00 +#define TBOOT_LOG_TARGET_VGA 0x01 +#define TBOOT_LOG_TARGET_SERIAL 0x02 +#define TBOOT_LOG_TARGET_MEMORY 0x04 +#define TBOOT_LOG_TARGET_EFI 0x10 + +uint8_t g_log_level; +uint8_t g_log_targets; +uint8_t g_vga_delay; +serial_port_t g_com_port; + +#define serial_init() comc_init() +#define serial_write(s, n) comc_puts(s, n) + +#define vga_write(s,n) vga_puts(s, n) + +#define efi_write(s,n) efi_puts(s, n) + +typedef enum { + INIT_EARLY_EFI, + INIT_PRE_LAUNCH, + INIT_POST_EBS, + INIT_POST_LAUNCH +} printk_init_t; + +void printk_init(printk_init_t init_type); +void printk(const char *fmt, ...) + __attribute__ ((format (printf, 1, 2))); + +#endif diff --git a/tboot/include/processor.h b/tboot/include/processor.h new file mode 100644 index 0000000..83b9fe4 --- /dev/null +++ b/tboot/include/processor.h @@ -0,0 +1,340 @@ +/* Copyright (c) 1991 The Regents of the University of California. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 4. Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + */ +/* + * Portions copyright (c) 2010, Intel Corporation + */ + +#ifndef __PROCESSOR_H__ +#define __PROCESSOR_H__ + +/* from: @(#)specialreg.h 7.1 (Berkeley) 5/9/91 + * $FreeBSD: stable/8/sys/i386/include/specialreg.h 198989 2009-11-06 15:24:48Z attilio $ + */ + +/* + * EFLAGS bits + */ +#define X86_EFLAGS_CF 0x00000001 /* Carry Flag */ +#define X86_EFLAGS_PF 0x00000004 /* Parity Flag */ +#define X86_EFLAGS_AF 0x00000010 /* Auxillary carry Flag */ +#define X86_EFLAGS_ZF 0x00000040 /* Zero Flag */ +#define X86_EFLAGS_SF 0x00000080 /* Sign Flag */ +#define X86_EFLAGS_TF 0x00000100 /* Trap Flag */ +#define X86_EFLAGS_IF 0x00000200 /* Interrupt Flag */ +#define X86_EFLAGS_DF 0x00000400 /* Direction Flag */ +#define X86_EFLAGS_OF 0x00000800 /* Overflow Flag */ +#define X86_EFLAGS_IOPL 0x00003000 /* IOPL mask */ +#define X86_EFLAGS_NT 0x00004000 /* Nested Task */ +#define X86_EFLAGS_RF 0x00010000 /* Resume Flag */ +#define X86_EFLAGS_VM 0x00020000 /* Virtual Mode */ +#define X86_EFLAGS_AC 0x00040000 /* Alignment Check */ +#define X86_EFLAGS_VIF 0x00080000 /* Virtual Interrupt Flag */ +#define X86_EFLAGS_VIP 0x00100000 /* Virtual Interrupt Pending */ +#define X86_EFLAGS_ID 0x00200000 /* CPUID detection flag */ + +/* + * Bits in 386 special registers: + */ +#define CR0_PE 0x00000001 /* Protected mode Enable */ +#define CR0_MP 0x00000002 /* "Math" (fpu) Present */ +#define CR0_EM 0x00000004 /* EMulate FPU instructions. (trap ESC only) */ +#define CR0_TS 0x00000008 /* Task Switched (if MP, trap ESC and WAIT) */ +#define CR0_ET 0x00000010 /* Extension type */ +#define CR0_PG 0x80000000 /* PaGing enable */ + +/* + * Bits in 486 special registers: + */ +#define CR0_NE 0x00000020 /* Numeric Error enable (EX16 vs IRQ13) */ +#define CR0_WP 0x00010000 /* Write Protect (honor page protect in all modes) */ +#define CR0_AM 0x00040000 /* Alignment Mask (set to enable AC flag) */ +#define CR0_NW 0x20000000 /* Not Write-through */ +#define CR0_CD 0x40000000 /* Cache Disable */ + +/* + * Bits in PPro special registers + */ +#define CR4_VME 0x00000001 /* Virtual 8086 mode extensions */ +#define CR4_PVI 0x00000002 /* Protected-mode virtual interrupts */ +#define CR4_TSD 0x00000004 /* Time stamp disable */ +#define CR4_DE 0x00000008 /* Debugging extensions */ +#define CR4_PSE 0x00000010 /* Page size extensions */ +#define CR4_PAE 0x00000020 /* Physical address extension */ +#define CR4_MCE 0x00000040 /* Machine check enable */ +#define CR4_PGE 0x00000080 /* Page global enable */ +#define CR4_PCE 0x00000100 /* Performance monitoring counter enable */ +#define CR4_FXSR 0x00000200/* Fast FPU save/restore used by OS */ +#define CR4_XMM 0x00000400 /* enable SIMD/MMX2 to use except 16 */ +#define CR4_VMXE 0x00002000/* enable VMX */ +#define CR4_SMXE 0x00004000/* enable SMX */ +#define CR4_PCIDE 0x00020000/* enable PCID */ + +#ifndef __ASSEMBLY__ + +/* from: + * $FreeBSD: src/sys/i386/include/cpufunc.h,v 1.158 2010/01/01 20:55:11 obrien Exp $ + */ + +static inline void do_cpuid(unsigned int ax, uint32_t *p) +{ + __asm__ __volatile__ ("cpuid" + : "=a" (p[0]), "=b" (p[1]), "=c" (p[2]), "=d" (p[3]) + : "0" (ax)); +} + +static inline void do_cpuid1(unsigned int ax, unsigned int cx, uint32_t *p) +{ + __asm__ __volatile__ ("cpuid" + : "=a" (p[0]), "=b" (p[1]), "=c" (p[2]), "=d" (p[3]) + : "0" (ax), "c" (cx)); +} + +static always_inline uint32_t cpuid_eax(unsigned int op) +{ + /* eax: regs[0], ebx: regs[1], ecx: regs[2], edx: regs[3] */ + uint32_t regs[4]; + + do_cpuid(op, regs); + + return regs[0]; +} + +static always_inline uint32_t cpuid_ebx(unsigned int op) +{ + /* eax: regs[0], ebx: regs[1], ecx: regs[2], edx: regs[3] */ + uint32_t regs[4]; + + do_cpuid(op, regs); + + return regs[1]; +} + +static always_inline uint32_t cpuid_ebx1(unsigned int op1, unsigned int op2) +{ + /* eax: regs[0], ebx: regs[1], ecx: regs[2], edx: regs[3] */ + uint32_t regs[4]; + + do_cpuid1(op1, op2, regs); + + return regs[1]; +} +static always_inline uint32_t cpuid_ecx(unsigned int op) +{ + /* eax: regs[0], ebx: regs[1], ecx: regs[2], edx: regs[3] */ + uint32_t regs[4]; + + do_cpuid(op, regs); + + return regs[2]; +} + +#define CPUID_X86_FEATURE_XMM3 (1<<0) +#define CPUID_X86_FEATURE_VMX (1<<5) +#define CPUID_X86_FEATURE_SMX (1<<6) + +/* Note, removed read/write ecx, not used */ + +static inline unsigned long long read_cr0(void) +{ + unsigned long long data; + /* 64: movl -> movq */ + __asm__ __volatile__ ("movq %%cr0,%0" : "=r" (data)); + return (data); +} + +static inline void write_cr0(unsigned long long data) +{ + /* 64: movl -> movq */ + __asm__ __volatile__("movq %0,%%cr0" : : "r" (data)); +} + +static inline unsigned long long read_cr4(void) +{ + unsigned long long data; + /* 64: movl -> movq */ + __asm__ __volatile__ ("movq %%cr4,%0" : "=r" (data)); + return (data); +} + +static inline void write_cr4(unsigned long long data) +{ + /* 64: movl -> movq */ + __asm__ __volatile__ ("movq %0,%%cr4" : : "r" (data)); +} + +static inline unsigned long long read_cr3(void) +{ + unsigned long long data; + /* 64: movl -> movq */ + __asm__ __volatile__ ("movq %%cr3,%0" : "=r" (data)); + return (data); +} + +static inline void write_cr3(unsigned long long data) +{ + /* 64: movl -> movq */ + __asm__ __volatile__("movq %0,%%cr3" : : "r" (data) : "memory"); +} + +static inline uint64_t read_rflags(void) +{ + uint64_t rf; + /* 32: EFLAGS stuff __asm__ __volatile__ ("pushfl; popl %0" : "=r" (ef));*/ + __asm__ __volatile__ ("pushfq; popq %0" : "=r" (rf)); + return (rf); +} + +static inline void write_rflags(uint64_t rf) +{ + /* 32: EFLAGS stuff __asm__ __volatile__ ("pushl %0; popfl" : : "r" (ef));*/ + __asm__ __volatile__ ("pushq %0; popfq" : : "r" (rf)); +} + +static inline void disable_intr(void) +{ + __asm__ __volatile__ ("cli" : : : "memory"); +} + +static inline void enable_intr(void) +{ + __asm__ __volatile__ ("sti"); +} + +/* was ia32_pause() */ +static inline void cpu_relax(void) +{ + __asm__ __volatile__ ("pause"); +} + +static inline void halt(void) +{ + __asm__ __volatile__ ("hlt"); +} + +static inline unsigned int get_apicid(void) +{ + return cpuid_ebx(1) >> 24; +} + +static inline void wbinvd(void) +{ + __asm__ __volatile__ ("wbinvd"); +} + +static inline uint32_t bsrl(uint32_t mask) +{ + uint32_t result; + + /* 64: Ok to shift 32b mask */ + __asm__ __volatile__ ("bsrl %1,%0" : "=r" (result) : "rm" (mask) : "cc"); + return (result); +} + +static inline int fls(int mask) +{ + return (mask == 0 ? mask : (int)bsrl((u_int)mask) + 1); +} + +static always_inline void mb(void) +{ + /* 32: __asm__ __volatile__ ("lock;addl $0,0(%%esp)" : : : "memory"); */ + __asm__ __volatile__ ("lock;addq $0,0(%%rsp)" : : : "memory"); +} + +static inline void cpu_monitor(const void *addr, int extensions, int hints) +{ + /* 64: a=rax, c=rcx, d=rdx ints are 32b into ecx, edx */ + __asm __volatile__ ("monitor;" : :"a" (addr), "c" (extensions), "d"(hints)); +} + +static inline void cpu_mwait(int extensions, int hints) +{ + /* 64: a=rax, c=rcx ints are 32b into eax, ecx */ + __asm __volatile__ ("mwait;" : :"a" (hints), "c" (extensions)); +} + +static inline void flush_tlb(void) +{ + __asm__ __volatile__ ( + "movq %%cr3, %%rax\n" + "movq %%rax, %%cr3\n" + : : : "rax"); +} + +typedef struct __packed lmode_desc { + uint16_t limit; + uint64_t base; +} lmode_desc_t; + +static inline void store_gdt(lmode_desc_t *gdt) +{ + __asm__ __volatile__("sgdt %0\n\t" + : "=m" (*gdt) : : "memory"); +} + +static inline void store_idt(lmode_desc_t *idt) +{ + __asm__ __volatile__("sidt %0\n\t" + : "=m" (*idt): : "memory"); +} + +#define lea_reference(i, o) __asm__ __volatile__ \ + ("lea "#i"(%%rip), %%rax\n\t" : "=a" (o)) + +#define mov_sel(r, o) __asm__ __volatile__ \ + ("movw %%"#r"s, %0\n\t" : "=m" (o) : : "memory"); + +/* In inline asm, these 3 use the A constraint to specify the EDX:EAX register + * pair. The inline assembler was getting the code badly wrong so the + * implementation of these moved to the assembly module (and renamed). + */ +uint64_t read_msr(uint32_t msr); +void write_msr(uint32_t msr, uint64_t newval); +uint64_t read_tsc(void); + +uint64_t get_rip(void); +uint64_t bsp_stack_ref(void); + +#define rdmsr read_msr +#define wrmsr write_msr +#define rdtsc read_tsc + +#endif /* __ASSEMBLY__ */ + +#endif /* __PROCESSOR_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/rijndael.h b/tboot/include/rijndael.h new file mode 100644 index 0000000..2974602 --- /dev/null +++ b/tboot/include/rijndael.h @@ -0,0 +1,58 @@ +/* $OpenBSD: rijndael.h,v 1.13 2008/06/09 07:49:45 djm Exp $ */ + +/** + * rijndael-alg-fst.h + * + * @version 3.0 (December 2000) + * + * Optimised ANSI C code for the Rijndael cipher (now AES) + * + * @author Vincent Rijmen + * @author Antoon Bosselaers + * @author Paulo Barreto + * + * This code is hereby placed in the public domain. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ''AS IS'' AND ANY EXPRESS + * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR + * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, + * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE + * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, + * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ +#ifndef __RIJNDAEL_H +#define __RIJNDAEL_H + +#define AES_MAXKEYBITS (256) +#define AES_MAXKEYBYTES (AES_MAXKEYBITS/8) +/* for 256-bit keys, fewer for less */ +#define AES_MAXROUNDS 14 + +//typedef unsigned char u8; +//typedef unsigned short u16; +//typedef unsigned int u32; + +/* The structure for key information */ +typedef struct { + int enc_only; /* context contains only encrypt schedule */ + int Nr; /* key-length-dependent number of rounds */ + u32 ek[4*(AES_MAXROUNDS + 1)]; /* encrypt key schedule */ + u32 dk[4*(AES_MAXROUNDS + 1)]; /* decrypt key schedule */ +} rijndael_ctx; + +int rijndael_set_key(rijndael_ctx *, const u_char *, int); +int rijndael_set_key_enc_only(rijndael_ctx *, const u_char *, int); +void rijndael_decrypt(rijndael_ctx *, const u_char *, u_char *); +void rijndael_encrypt(rijndael_ctx *, const u_char *, u_char *); + +int rijndaelKeySetupEnc(unsigned int [], const unsigned char [], int); +int rijndaelKeySetupDec(unsigned int [], const unsigned char [], int); +void rijndaelEncrypt(const unsigned int [], int, const unsigned char [], + unsigned char []); + +#endif /* __RIJNDAEL_H */ diff --git a/tboot/include/sha1.h b/tboot/include/sha1.h new file mode 100644 index 0000000..10d89df --- /dev/null +++ b/tboot/include/sha1.h @@ -0,0 +1,77 @@ +/*$FreeBSD: src/sys/crypto/sha1.h,v 1.8.36.1.2.1 2009/10/25 01:10:29 kensmith Exp $ */ +/*$KAME: sha1.h,v 1.5 2000/03/27 04:36:23 sumikawa Exp $ */ + +/* + * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of the project nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ +/* + * Portions copyright (c) 2010, Intel Corporation + */ + +/* + * FIPS pub 180-1: Secure Hash Algorithm (SHA-1) + * based on: http://csrc.nist.gov/fips/fip180-1.txt + * implemented by Jun-ichiro itojun Itoh + */ + +#ifndef __SHA1_H__ +#define __SHA1_H__ + +struct sha1_ctxt { + union { + uint8_t b8[20]; + uint32_t b32[5]; + } h; + union { + uint8_t b8[8]; + uint64_t b64[1]; + } c; + union { + uint8_t b8[64]; + uint32_t b32[16]; + } m; + uint8_t count; +}; + +void sha1_init(struct sha1_ctxt *); +void sha1_pad(struct sha1_ctxt *); +void sha1_loop(struct sha1_ctxt *, const uint8_t *, size_t); +void sha1_result(struct sha1_ctxt *, unsigned char *); +#define SHA1_RESULTLEN (160/8) + +/* compatibilty with other SHA1 source codes */ +typedef struct sha1_ctxt SHA_CTX; +#define SHA1_Init(x) sha1_init((x)) +#define SHA1_Update(x, y, z) sha1_loop((x), (y), (z)) +#define SHA1_Final(x, y) sha1_result((y), (x)) +#define SHA_DIGEST_LENGTH SHA1_RESULTLEN + +int sha1_buffer(const unsigned char *buffer, size_t len, + unsigned char md[SHA_DIGEST_LENGTH]); + +#endif /* __SHA1_H__ */ diff --git a/tboot/include/sha256.h b/tboot/include/sha256.h new file mode 100644 index 0000000..2c3fc56 --- /dev/null +++ b/tboot/include/sha256.h @@ -0,0 +1,30 @@ +#ifndef __SHA256_H__ +#define __SHA256_H__ + +#define STORE64H(x, y) \ + { (y)[0] = (unsigned char)(((x)>>56)&255); (y)[1] = (unsigned char)(((x)>>48)&255); \ + (y)[2] = (unsigned char)(((x)>>40)&255); (y)[3] = (unsigned char)(((x)>>32)&255); \ + (y)[4] = (unsigned char)(((x)>>24)&255); (y)[5] = (unsigned char)(((x)>>16)&255); \ + (y)[6] = (unsigned char)(((x)>>8)&255); (y)[7] = (unsigned char)((x)&255); } + +#define STORE32H(x, y) \ + { (y)[0] = (unsigned char)(((x)>>24)&255); (y)[1] = (unsigned char)(((x)>>16)&255); \ + (y)[2] = (unsigned char)(((x)>>8)&255); (y)[3] = (unsigned char)((x)&255); } + +#define LOAD32H(x, y) \ + { x = ((unsigned long)((y)[0] & 255)<<24) | \ + ((unsigned long)((y)[1] & 255)<<16) | \ + ((unsigned long)((y)[2] & 255)<<8) | \ + ((unsigned long)((y)[3] & 255)); } + +typedef struct { + u64 length; + u32 state[8], curlen; + unsigned char buf[64]; +}sha256_state; + +void sha256_buffer(const unsigned char *buffer, size_t len, + unsigned char hash[32]); + +#endif /* __SHA256_H__ */ + diff --git a/tboot/include/string.h b/tboot/include/string.h new file mode 100644 index 0000000..30b571b --- /dev/null +++ b/tboot/include/string.h @@ -0,0 +1,73 @@ +/*- + * Copyright (c) 1992, 1993 + * The Regents of the University of California. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 4. Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * @(#)libkern.h 8.1 (Berkeley) 6/10/93 + * $FreeBSD: src/sys/sys/libkern.h,v 1.60 2009/02/14 11:34:57 rrs Exp $ + */ +/* + * Portions copyright (c) 2010, Intel Corporation + */ + +#ifndef __STRING_H__ +#define __STRING_H__ + +#include +#include + +int memcmp(const void *b1, const void *b2, size_t len); +char *index(const char *, int); +int strcmp(const char *, const char *); +size_t strlen(const char *); +int strncmp(const char *, const char *, size_t); +char *strncpy(char * __restrict, const char * __restrict, size_t); +void *memcpy(void *dst, const void *src, size_t len); +int snprintf(char *buf, size_t size, const char *fmt, ...); +int vscnprintf(char *buf, size_t size, const char *fmt, va_list ap); +unsigned long strtoul(const char *nptr, char **endptr, int base); + +static inline void *memset(void *b, int c, size_t len) +{ + char *bb; + + for (bb = (char *)b; len--; ) + *bb++ = c; + + return (b); +} + +static inline void *memmove(void *dest, const void *src, size_t n) +{ + return memcpy(dest, src, n); +} + +static __inline char *strchr(const char *p, int ch) +{ + return index(p, ch); +} + +#endif /* __STRING_H__ */ diff --git a/tboot/include/tb_error.h b/tboot/include/tb_error.h new file mode 100644 index 0000000..428fd51 --- /dev/null +++ b/tboot/include/tb_error.h @@ -0,0 +1,89 @@ +/* + * tb_error.h: error code definitions + * + * Copyright (c) 2006-2007, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TB_ERROR_H__ +#define __TB_ERROR_H__ + +typedef enum { + TB_ERR_NONE = 0, /* succeed */ + TB_ERR_FIXED = 1, /* previous error has been fixed */ + + TB_ERR_GENERIC, /* non-fatal generic error */ + + TB_ERR_TPM_NOT_READY, /* tpm not ready */ + TB_ERR_SMX_NOT_SUPPORTED, /* smx not supported */ + TB_ERR_VMX_NOT_SUPPORTED, /* vmx not supported */ + TB_ERR_TXT_NOT_SUPPORTED, /* txt not supported */ + + TB_ERR_MODULE_VERIFICATION_FAILED, /* module failed to verify against + policy */ + TB_ERR_MODULES_NOT_IN_POLICY, /* modules in mbi but not in + policy */ + TB_ERR_POLICY_INVALID, /* policy is invalid */ + TB_ERR_POLICY_NOT_PRESENT, /* no policy in TPM NV */ + + TB_ERR_SINIT_NOT_PRESENT, /* SINIT ACM not provided */ + TB_ERR_ACMOD_VERIFY_FAILED, /* verifying AC module failed */ + + TB_ERR_POST_LAUNCH_VERIFICATION, /* verification of post-launch + failed */ + TB_ERR_S3_INTEGRITY, /* creation or verification of + S3 integrity measurements + failed */ + + TB_ERR_FATAL, /* generic fatal error */ + TB_ERR_NV_VERIFICATION_FAILED, /* NV failed to verify against + policy */ + TB_ERR_MAX +} tb_error_t; + + +void print_tb_error_msg(tb_error_t error); +bool read_tb_error_code(tb_error_t *error); +bool write_tb_error_code(tb_error_t error); +bool was_last_boot_error(void); + + +#endif /* __TB_ERROR_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/tb_policy.h b/tboot/include/tb_policy.h new file mode 100644 index 0000000..118a735 --- /dev/null +++ b/tboot/include/tb_policy.h @@ -0,0 +1,388 @@ +/* + * tb_policy.h: data structures, definitions, and helper fns for tboot + * verified launch policies + * + * Copyright (c) 2006-2010, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TB_POLICY_H__ +#define __TB_POLICY_H__ + +/* + * policy types + */ +enum { + TB_POLTYPE_CONT_NON_FATAL, /* ignore all non-fatal errors and */ + /* continue */ + TB_POLTYPE_CONT_VERIFY_FAIL, /* ignore verification errors and */ + /* halt otherwise */ + TB_POLTYPE_HALT, /* halt on any errors */ + TB_POLTYPE_MAX +}; + +/* + * policy hash types + */ +enum { + TB_HTYPE_ANY, + TB_HTYPE_IMAGE, +}; + + +#define TB_POL_MAX_MOD_NUM 127 /* largest supported module number */ +#define TB_POL_MOD_NUM_ANY 129 /* matches any module number */ + /* (should be last entry of modules) */ +#define TB_POL_MOD_NUM_NV 130 /* indicate this is a nv index entry */ +#define TB_POL_MOD_NUM_NV_RAW 131 /* a nv entry verified by raw content */ + +#define TB_POL_MAX_PCR 23 /* largest supported PCR number */ +#define TB_POL_PCR_NONE 255 /* don't extend measurement into a PCR */ + + +/* + * policies + */ + +typedef struct __packed { + uint8_t mod_num; /* 0-based or TB_POL_MOD_NUM_* */ + uint8_t pcr; /* PCR number (0-23) or TB_POL_PCR_* */ + uint8_t hash_type; /* TB_HTYPE_* */ + uint32_t nv_index; /* nv index to be measured, effective when */ + /* mod_num==TB_POL_MOD_NUM_{NV | NV_RAW} */ + /* mod_num: */ + /* TB_POL_MOD_NUM_NV_RAW: */ + /* check index size==hash size, */ + /* no hashing before verify and extend */ + /* TB_POL_MOD_NUM_NV: */ + /* hashing before verify and extend */ + uint8_t num_hashes; + tb_hash_t hashes[]; +} tb_policy_entry_t; + +#define TB_POLCTL_EXTEND_PCR17 0x1 /* extend policy into PCR 17 */ + +typedef struct __packed { + uint8_t version; /* currently 2 */ + uint8_t policy_type; /* TB_POLTYPE_* */ + /* TODO should be changed to 16bit for TPM 2.0 */ + uint8_t hash_alg; /* TB_HALG_* */ + uint32_t policy_control; /* bitwise OR of TB_POLCTL_* */ + uint32_t reserved; + uint8_t num_entries; + tb_policy_entry_t entries[]; +} tb_policy_t; + +/* + * TPM NV index for VL policy + */ + +/* max size of policy in TPM NV (assumes 8 entries w/ 4 hashes each) */ +#define MAX_TB_POLICY_SIZE \ + sizeof(tb_policy_t) + 8*(sizeof(tb_policy_entry_t) + 4*sizeof(tb_hash_t)) + +#define TB_POLICY_INDEX 0x20000001 /* policy index for Verified Launch */ + + +/* + * helper fns + */ +#ifndef PRINT +#define PRINT(...) {} +#endif + +static inline const char *hash_type_to_string(uint8_t hash_type) +{ + if ( hash_type == TB_HTYPE_ANY ) + return "TB_HTYPE_ANY"; + else if ( hash_type == TB_HTYPE_IMAGE ) + return "TB_HTYPE_IMAGE"; + else { + static char buf[32]; + snprintf(buf, sizeof(buf), "unsupported (%u)", hash_type); + return buf; + } +} + +static inline const char *policy_type_to_string(uint8_t policy_type) +{ + if ( policy_type == TB_POLTYPE_CONT_NON_FATAL ) + return "TB_POLTYPE_CONT_NON_FATAL"; + else if ( policy_type == TB_POLTYPE_CONT_VERIFY_FAIL ) + return "TB_POLTYPE_CONT_VERIFY_FAIL"; + else if ( policy_type == TB_POLTYPE_HALT ) + return "TB_POLTYPE_HALT"; + else { + static char buf[32]; + snprintf(buf, sizeof(buf), "unsupported (%u)", policy_type); + return buf; + } +} + +static inline const char *policy_control_to_string(uint32_t policy_control) +{ + static char buf[64] = ""; + + if ( policy_control & TB_POLCTL_EXTEND_PCR17 ) + strncpy(buf, "EXTEND_PCR17", sizeof(buf)); + + return buf; +} + +static inline size_t calc_policy_entry_size(const tb_policy_entry_t *pol_entry, + uint16_t hash_alg) +{ + if ( pol_entry == NULL ) + return 0; + + size_t size = sizeof(*pol_entry); + /* tb_policy_entry_t has empty hash array, which isn't counted in size */ + /* so add size of each hash */ + size += pol_entry->num_hashes * get_hash_size(hash_alg); + + return size; +} + +static inline size_t calc_policy_size(const tb_policy_t *policy) +{ + size_t size = sizeof(*policy); + + /* tb_policy_t has empty array, which isn't counted in size */ + /* so add size of each policy */ + const tb_policy_entry_t *pol_entry = policy->entries; + for ( int i = 0; i < policy->num_entries; i++ ) { + size_t entry_size = calc_policy_entry_size(pol_entry, + policy->hash_alg); + pol_entry = (void *)pol_entry + entry_size; + size += entry_size; + } + + return size; +} + +static inline tb_hash_t *get_policy_entry_hash( + const tb_policy_entry_t *pol_entry, uint16_t hash_alg, int i) +{ + /* assumes policy has already been validated */ + + if ( pol_entry == NULL ) { + PRINT(TBOOT_ERR"Error: pol_entry pointer is NULL\n"); + return NULL; + } + + if ( i < 0 || i >= pol_entry->num_hashes ) { + PRINT(TBOOT_ERR"Error: position is not correct.\n"); + return NULL; + } + + return (tb_hash_t *)((void *)pol_entry->hashes + + i * get_hash_size(hash_alg)); +} + +static inline tb_policy_entry_t* get_policy_entry(const tb_policy_t *policy, + int i) +{ + /* assumes policy has already been validated */ + + if ( policy == NULL ) { + PRINT(TBOOT_ERR"Error: policy pointer is NULL\n"); + return NULL; + } + + if ( i < 0 || i >= policy->num_entries ) { + PRINT(TBOOT_ERR"Error: position is not correct.\n"); + return NULL; + } + + tb_policy_entry_t *pol_entry = (tb_policy_entry_t *)policy->entries; + for ( int j = 0; j < i; j++ ) { + pol_entry = (void *)pol_entry + + calc_policy_entry_size(pol_entry, policy->hash_alg); + } + + return pol_entry; +} + +static inline tb_policy_entry_t* find_policy_entry(const tb_policy_t *policy, + uint8_t mod_num) +{ + /* assumes policy has already been validated */ + + if ( policy == NULL ) { + PRINT(TBOOT_ERR"Error: policy pointer is NULL\n"); + return NULL; + } + + for ( int i = 0; i < policy->num_entries; i++ ) { + tb_policy_entry_t *pol_entry = get_policy_entry(policy, i); + if ( pol_entry == NULL ) + return NULL; + + if ( pol_entry->mod_num == mod_num || + pol_entry->mod_num == TB_POL_MOD_NUM_ANY ) + return pol_entry; + } + + return NULL; +} + +/* + * verify and display policy + */ +static inline bool verify_policy(const tb_policy_t *policy, size_t size, bool print) +{ + if ( print ) PRINT(TBOOT_DETA"policy:\n"); + + if ( policy == NULL ) { + if ( print ) PRINT(TBOOT_ERR"policy pointer is NULL\n"); + return false; + } + + if ( size < sizeof(tb_policy_t) ) { + if ( print ) PRINT(TBOOT_ERR"size of policy is too small (%lu)\n", + (unsigned long)size); + return false; + } + + if ( policy->version != 0x02 ) { + if ( print ) PRINT(TBOOT_ERR"unsupported version (%u)\n", policy->version); + return false; + } + if ( print ) PRINT(TBOOT_DETA"\t version: %u\n", policy->version); + + if ( print ) PRINT(TBOOT_DETA"\t policy_type: %s\n", + policy_type_to_string(policy->policy_type)); + if ( policy->policy_type >= TB_POLTYPE_MAX ) + return false; + + if ( print ) PRINT(TBOOT_DETA"\t hash_alg: %s\n", + hash_alg_to_string(policy->hash_alg)); + + if ( print ) PRINT(TBOOT_DETA"\t policy_control: %08x (%s)\n", + policy->policy_control, + policy_control_to_string(policy->policy_control)); + + if ( print ) PRINT(TBOOT_DETA"\t num_entries: %u\n", policy->num_entries); + + const tb_policy_entry_t *pol_entry = policy->entries; + for ( int i = 0; i < policy->num_entries; i++ ) { + /* check header of policy entry */ + if ( ((void *)pol_entry - (void *)policy + sizeof(*pol_entry)) > + size ) { + if ( print ) PRINT(TBOOT_ERR"size of policy entry is too small (%lu)\n", + (unsigned long)size); + return false; + } + + if ( print ) PRINT(TBOOT_DETA"\t policy entry[%d]:\n", i); + + if ( pol_entry->mod_num > TB_POL_MAX_MOD_NUM && + pol_entry->mod_num != TB_POL_MOD_NUM_ANY && + pol_entry->mod_num != TB_POL_MOD_NUM_NV && + pol_entry->mod_num != TB_POL_MOD_NUM_NV_RAW ) { + if ( print ) PRINT(TBOOT_ERR"mod_num invalid (%u)\n", pol_entry->mod_num); + return false; + } + if ( print ) PRINT(TBOOT_DETA"\t\t mod_num: "); + if ( pol_entry->mod_num == TB_POL_MOD_NUM_ANY ) { + if ( print ) PRINT(TBOOT_DETA"any\n"); + } + else if ( pol_entry->mod_num == TB_POL_MOD_NUM_NV ) { + if ( print ) + PRINT(TBOOT_DETA"nv\n" + "\t\t nv_index: %08x\n", + pol_entry->nv_index); + } + else if ( pol_entry->mod_num == TB_POL_MOD_NUM_NV_RAW ) { + if ( print ) + PRINT(TBOOT_DETA"nv_raw\n" + "\t\t nv_index: %08x\n", + pol_entry->nv_index); + } + else + if ( print ) PRINT(TBOOT_DETA"%u\n", pol_entry->mod_num); + + if ( pol_entry->pcr > TB_POL_MAX_PCR && + pol_entry->pcr != TB_POL_PCR_NONE ) { + if ( print ) PRINT(TBOOT_ERR"pcr invalid (%u)\n", pol_entry->pcr); + return false; + } + if ( print ) PRINT(TBOOT_DETA"\t\t pcr: "); + if ( pol_entry->pcr == TB_POL_PCR_NONE ) { + if ( print ) PRINT(TBOOT_DETA"none\n"); + } + else + if ( print ) PRINT(TBOOT_DETA"%u\n", pol_entry->pcr); + + if ( print ) PRINT(TBOOT_DETA"\t\t hash_type: %s\n", + hash_type_to_string(pol_entry->hash_type)); + if ( pol_entry->hash_type > TB_HTYPE_IMAGE ) + return false; + + if ( print ) PRINT(TBOOT_DETA"\t\t num_hashes: %u\n", pol_entry->num_hashes); + + /* check all of policy */ + if ( ((void *)pol_entry - (void *)policy + sizeof(*pol_entry) + + pol_entry->num_hashes * get_hash_size(policy->hash_alg)) + > size ) { + if ( print ) PRINT(TBOOT_ERR"size of policy entry is too small (%lu)\n", + (unsigned long)size); + return false; + } + + for ( int j = 0; j < pol_entry->num_hashes; j++ ) { + if ( print ) { + PRINT(TBOOT_DETA"\t\t hashes[%d]: ", j); + print_hash(get_policy_entry_hash(pol_entry, + policy->hash_alg, j), + policy->hash_alg); + } + } + + pol_entry = (void *)pol_entry + + calc_policy_entry_size(pol_entry, policy->hash_alg); + } + + return true; +} + +#endif /* __TB_POLICY_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ + diff --git a/tboot/include/tboot.h b/tboot/include/tboot.h new file mode 100644 index 0000000..ecf7dbe --- /dev/null +++ b/tboot/include/tboot.h @@ -0,0 +1,197 @@ +/* + * tboot.h: shared data structure with MLE and kernel and functions + * used by kernel for runtime support + * + * Copyright (c) 2006-2010, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ +#ifndef __TBOOT_H__ +#define __TBOOT_H__ + +#ifndef __packed +#define __packed __attribute__ ((packed)) +#endif + +#define TB_CURRENT_VER 7 + +/* define uuid_t here in case uuid.h wasn't pre-included */ +/* (i.e. so tboot.h can be self-sufficient) */ +#ifndef __UUID_H__ +typedef struct __packed { + uint32_t data1; + uint16_t data2; + uint16_t data3; + uint16_t data4; + uint8_t data5[6]; +} uuid_t; +#endif + +/* + * used to communicate between tboot and the launched kernel (i.e. Xen) + */ + +#define TB_KEY_SIZE 64 /* 512 bits */ + +#define MAX_TB_MAC_REGIONS 32 +typedef struct __packed { + uint64_t start; /* must be 4k byte -aligned */ + uint32_t size; /* must be 4k byte -granular */ +} tboot_mac_region_t; + +/* GAS - Generic Address Structure (ACPI 2.0+) */ +typedef struct __packed { + uint8_t space_id; /* only 0,1 (memory, I/O) are supported */ + uint8_t bit_width; + uint8_t bit_offset; + uint8_t access_width; /* only 1-3 (byte, word, dword) are supported */ + uint64_t address; +} tboot_acpi_generic_address_t; + +typedef struct __packed { + tboot_acpi_generic_address_t pm1a_cnt_blk; + tboot_acpi_generic_address_t pm1b_cnt_blk; + tboot_acpi_generic_address_t pm1a_evt_blk; + tboot_acpi_generic_address_t pm1b_evt_blk; + uint16_t pm1a_cnt_val; + uint16_t pm1b_cnt_val; + uint64_t wakeup_vector; + uint32_t vector_width; + uint64_t kernel_s3_resume_vector; +} tboot_acpi_sleep_info_t; + +#define TB_RESMEM_BLOCKS 128 + +typedef struct __packed { + uint64_t addr; + uint64_t length; +} reserve_map_t; + +typedef struct __packed { + /* version 3+ fields: */ + uuid_t uuid; /* {663C8DFF-E8B3-4b82-AABF-19EA4D057A08} */ + uint32_t version; /* currently 7 for EFI support */ + uint32_t log_addr; /* physical addr of log or NULL if none */ + uint32_t shutdown_entry; /* entry point for tboot shutdown */ + uint32_t shutdown_type; /* type of shutdown (TB_SHUTDOWN_*) */ + tboot_acpi_sleep_info_t + acpi_sinfo; /* where kernel put acpi sleep info in Sx */ + uint32_t tboot_base; /* starting addr for tboot */ + uint32_t tboot_size; /* size of tboot */ + uint8_t num_mac_regions; /* number mem regions to MAC on S3 */ + /* contig regions memory to MAC on S3 */ + tboot_mac_region_t mac_regions[MAX_TB_MAC_REGIONS]; + /* version 4+ fields: */ + /* populated by tboot; will be encrypted */ + uint8_t s3_key[TB_KEY_SIZE]; + /* version 5+ fields: */ + uint8_t reserved_align[3]; /* used to 4byte-align num_in_wfs */ + uint32_t num_in_wfs; /* number of processors in wait-for-SIPI */ + /* version 6+ fields: */ + uint32_t flags; + uint64_t ap_wake_addr; /* phys addr of kernel/VMM SIPI vector */ + uint32_t ap_wake_trigger; /* kernel/VMM writes APIC ID to wake AP */ + /* version 7+ fields */ + /* reserve mem blocks to adjust dom0 E820 */ + uint64_t reserve_map_count; + reserve_map_t reserve_map[TB_RESMEM_BLOCKS]; +} tboot_shared_t; + +#define TB_SHUTDOWN_REBOOT 0 +#define TB_SHUTDOWN_S5 1 +#define TB_SHUTDOWN_S4 2 +#define TB_SHUTDOWN_S3 3 +#define TB_SHUTDOWN_HALT 4 +#define TB_SHUTDOWN_WFS 5 + +#define TB_FLAG_AP_WAKE_SUPPORT 0x00000001 /* kernel/VMM use INIT-SIPI-SIPI + if clear, ap_wake_* if set */ + +/* {663C8DFF-E8B3-4b82-AABF-19EA4D057A08} */ +#define TBOOT_SHARED_UUID {0x663c8dff, 0xe8b3, 0x4b82, 0xaabf, \ + {0x19, 0xea, 0x4d, 0x5, 0x7a, 0x8 }} +#define TBOOT_MEM_LOG_SIZE 0x8000 +/* + * used to log tboot printk output + */ +typedef struct { + uuid_t uuid; + bool is_init; + uint16_t max_size; + uint16_t curr_pos; + char buf[TBOOT_MEM_LOG_SIZE]; +} tboot_log_t; + +/* {C0192526-6B30-4db4-844C-A3E953B88174} */ +#define TBOOT_LOG_UUID {0xc0192526, 0x6b30, 0x4db4, 0x844c, \ + {0xa3, 0xe9, 0x53, 0xb8, 0x81, 0x74 }} + +/* The tboot_shared page */ +tboot_shared_t _tboot_shared; + +long s3_flag; + +static inline void print_tboot_shared(const tboot_shared_t *tboot_shared) +{ + printk(TBOOT_DETA"tboot_shared data:\n"); + printk(TBOOT_DETA"\t version: %d\n", tboot_shared->version); + printk(TBOOT_DETA"\t log_addr: 0x%08x\n", tboot_shared->log_addr); + printk(TBOOT_DETA"\t shutdown_entry: 0x%08x\n", tboot_shared->shutdown_entry); + printk(TBOOT_DETA"\t shutdown_type: %d\n", tboot_shared->shutdown_type); + printk(TBOOT_DETA"\t tboot_base: 0x%08x\n", tboot_shared->tboot_base); + printk(TBOOT_DETA"\t tboot_size: 0x%x\n", tboot_shared->tboot_size); + printk(TBOOT_DETA"\t num_in_wfs: %u\n", tboot_shared->num_in_wfs); + printk(TBOOT_DETA"\t flags: 0x%8.8x\n", tboot_shared->flags); + printk(TBOOT_DETA"\t ap_wake_addr: 0x%08x\n", (uint32_t)tboot_shared->ap_wake_addr); + printk(TBOOT_DETA"\t ap_wake_trigger: %u\n", tboot_shared->ap_wake_trigger); +} + +void begin_initial_launch(void); +void begin_launch(efi_xen_tboot_data_t *xtd); +void s3_launch(void); +void shutdown(void); +void cpu_wakeup(uint32_t cpuid, uint64_t sipi_vec); + +/* policy */ +void verify_all_modules(void); +void apply_policy(tb_error_t error); +tb_error_t set_policy(void); + +#endif /* __TBOOT_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/tpm.h b/tboot/include/tpm.h new file mode 100644 index 0000000..59ebde1 --- /dev/null +++ b/tboot/include/tpm.h @@ -0,0 +1,521 @@ +/* + * tpm.h: TPM-related support functions + * + * Copyright (c) 2006-2009, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TPM_H__ +#define __TPM_H__ + +#include +#include +#include +#include + +/* un-comment to enable detailed command tracing */ +//#define TPM_TRACE + +#define TPM_IF_12 0 +#define TPM_IF_20_FIFO 1 +#define TPM_IF_20_CRB 2 + +#define TPM_INTERFACE_ID_FIFO_20 0x0 +#define TPM_INTERFACE_ID_CRB 0x1 +#define TPM_INTERFACE_ID_FIFO_13 0xF + +#define TPM_LOCALITY_BASE 0xfed40000 +#define TPM_LOCALITY_0 TPM_LOCALITY_BASE +#define TPM_LOCALITY_1 (TPM_LOCALITY_BASE | 0x1000) +#define TPM_LOCALITY_2 (TPM_LOCALITY_BASE | 0x2000) +#define TPM_LOCALITY_3 (TPM_LOCALITY_BASE | 0x3000) +#define TPM_LOCALITY_4 (TPM_LOCALITY_BASE | 0x4000) +#define TPM_LOCALITY_BASE_N(n) (TPM_LOCALITY_BASE | ((n) << 12)) +#define TPM_NR_LOCALITIES 5 +#define NR_TPM_LOCALITY_PAGES ((TPM_LOCALITY_1 - TPM_LOCALITY_0) >> PAGE_SHIFT) + +#define TPM_LOCALITY_CRB_BASE 0xfed40000 +#define TPM_LOCALITY_CRB_0 TPM_LOCALITY_CRB_BASE +#define TPM_LOCALITY_CRB_1 (TPM_LOCALITY_CRB_BASE | 0x1000) +#define TPM_LOCALITY_CRB_2 (TPM_LOCALITY_CRB_BASE | 0x2000) +#define TPM_LOCALITY_CRB_3 (TPM_LOCALITY_CRB_BASE | 0x3000) +#define TPM_LOCALITY_CRB_4 (TPM_LOCALITY_CRB_BASE | 0x4000) +#define TPM_LOCALITY_CRB_BASE_N(n) (TPM_LOCALITY_CRB_BASE | ((n) << 12)) +#define TPM_NR_CRB_LOCALITIES 5 +#define NR_TPM_LOCALITY_CRB_PAGES ((TPM_LOCALITY_CRB_1 - TPM_LOCALITY_CRB_0) >> PAGE_SHIFT) +/* + * Command Header Fields: + * 0 1 2 3 4 5 6 7 8 9 10 ... + * ------------------------------------------------------------- + * | TAG | SIZE | COMMAND CODE | other ... + * ------------------------------------------------------------- + * + * Response Header Fields: + * 0 1 2 3 4 5 6 7 8 9 10 ... + * ------------------------------------------------------------- + * | TAG | SIZE | RETURN CODE | other ... + * ------------------------------------------------------------- + */ +#define CMD_HEAD_SIZE 10 +#define RSP_HEAD_SIZE 10 +#define CMD_SIZE_OFFSET 2 +#define CMD_CC_OFFSET 6 +#define RSP_SIZE_OFFSET 2 +#define RSP_RST_OFFSET 6 + +/* + * The term timeout applies to timings between various states + * or transitions within the interface protocol. + */ +#define TIMEOUT_UNIT (0x100000 / 330) /* ~1ms, 1 tpm r/w need > 330ns */ +#define TIMEOUT_A 750 /* 750ms */ +#define TIMEOUT_B 2000 /* 2s */ +#define TIMEOUT_C 75000 /* 750ms */ +#define TIMEOUT_D 750 /* 750ms */ + +typedef struct __packed { + uint32_t timeout_a; + uint32_t timeout_b; + uint32_t timeout_c; + uint32_t timeout_d; +} tpm_timeout_t; + +/* + * The TCG maintains a registry of all algorithms that have an + * assigned algorithm ID. That registry is the definitive list + * of algorithms that may be supported by a TPM. + */ +#define TPM_ALG_ERROR 0x0000 +#define TPM_ALG_FIRST 0x0001 +#define TPM_ALG_RSA 0x0001 +#define TPM_ALG_DES 0x0002 +#define TPM_ALG__3DES 0x0003 +#define TPM_ALG_SHA 0x0004 +#define TPM_ALG_SHA1 0x0004 +#define TPM_ALG_HMAC 0x0005 +#define TPM_ALG_AES 0x0006 +#define TPM_ALG_MGF1 0x0007 +#define TPM_ALG_KEYEDHASH 0x0008 +#define TPM_ALG_XOR 0x000A +#define TPM_ALG_SHA256 0x000B +#define TPM_ALG_SHA384 0x000C +#define TPM_ALG_SHA512 0x000D +#define TPM_ALG_WHIRLPOOL512 0x000E +#define TPM_ALG_NULL 0x0010 +#define TPM_ALG_SM3_256 0x0012 +#define TPM_ALG_SM4 0x0013 +#define TPM_ALG_RSASSA 0x0014 +#define TPM_ALG_RSAES 0x0015 +#define TPM_ALG_RSAPSS 0x0016 +#define TPM_ALG_OAEP 0x0017 +#define TPM_ALG_ECDSA 0x0018 +#define TPM_ALG_ECDH 0x0019 +#define TPM_ALG_ECDAA 0x001A +#define TPM_ALG_SM2 0x001B +#define TPM_ALG_ECSCHNORR 0x001C +#define TPM_ALG_KDF1_SP800_56a 0x0020 +#define TPM_ALG_KDF2 0x0021 +#define TPM_ALG_KDF1_SP800_108 0x0022 +#define TPM_ALG_ECC 0x0023 +#define TPM_ALG_SYMCIPHER 0x0025 +#define TPM_ALG_CTR 0x0040 +#define TPM_ALG_OFB 0x0041 +#define TPM_ALG_CBC 0x0042 +#define TPM_ALG_CFB 0x0043 +#define TPM_ALG_ECB 0x0044 +#define TPM_ALG_LAST 0x0044 +#define TPM_ALG_MAX_NUM (TPM_ALG_LAST - TPM_ALG_ERROR) + + +// move from tpm.c + +/* + * TPM registers and data structures + * + * register values are offsets from each locality base + * see {read,write}_tpm_reg() for data struct format + */ + +/* TPM_ACCESS_x */ +#define TPM_REG_ACCESS 0x00 +#define TPM_REG_STS 0x18 + +typedef union { + u8 _raw[1]; /* 1-byte reg */ + struct __packed { + u8 tpm_establishment : 1; /* RO, 0=T/OS has been established + before */ + u8 request_use : 1; /* RW, 1=locality is requesting TPM use */ + u8 pending_request : 1; /* RO, 1=other locality is requesting + TPM usage */ + u8 seize : 1; /* WO, 1=seize locality */ + u8 been_seized : 1; /* RW, 1=locality seized while active */ + u8 active_locality : 1; /* RW, 1=locality is active */ + u8 reserved : 1; + u8 tpm_reg_valid_sts : 1; /* RO, 1=other bits are valid */ + }; +} tpm_reg_access_t; + +/* TPM_STS_x */ + +typedef union { + u8 _raw[3]; /* 3-byte reg */ + struct __packed { + u8 reserved1 : 1; + u8 response_retry : 1; /* WO, 1=re-send response */ + u8 self_test_done : 1; /* RO, only for version 2 */ + u8 expect : 1; /* RO, 1=more data for command expected */ + u8 data_avail : 1; /* RO, 0=no more data for response */ + u8 tpm_go : 1; /* WO, 1=execute sent command */ + u8 command_ready : 1; /* RW, 1=TPM ready to receive new cmd */ + u8 sts_valid : 1; /* RO, 1=data_avail and expect bits are valid */ + u16 burst_count : 16; /* RO, # read/writes bytes before wait */ + }; +} tpm12_reg_sts_t; + +typedef union { + u8 _raw[4]; /* 4-byte reg */ + struct __packed { + u8 reserved1 : 1; + u8 response_retry : 1; /* WO, 1=re-send response */ + u8 self_test_done : 1; /* RO, only for version 2 */ + u8 expect : 1; /* RO, 1=more data for command expected */ + u8 data_avail : 1; /* RO, 0=no more data for response */ + u8 tpm_go : 1; /* WO, 1=execute sent command */ + u8 command_ready : 1; /* RW, 1=TPM ready to receive new cmd */ + u8 sts_valid : 1; /* RO, 1=data_avail and expect bits are + valid */ + u16 burst_count : 16; /* RO, # read/writes bytes before wait */ + /* version >= 2 */ + u8 command_cancel : 1; + u8 reset_establishment : 1; + u8 tpm_family : 2; + u8 reserved2 : 4; + }; +} tpm20_reg_sts_t; + +//----------------------------------------------------------------------------- +// CRB I/F related definitions, see TCG PC Client Platform TPM Profile (PTP) Specification, Level 00 Revision 00.43 +//----------------------------------------------------------------------------- +#define TPM_REG_LOC_STATE 0x00 +#define TPM_REG_LOC_CTRL 0x8 +#define TPM_LOCALITY_STS 0x0C +#define TPM_INTERFACE_ID 0x30 +#define TPM_CONTROL_AREA 0x40 +#define TPM_CRB_CTRL_REQ 0x40 +#define TPM_CRB_CTRL_STS 0x44 +#define TPM_CRB_CTRL_CANCEL 0x48 +#define TPM_CRB_CTRL_START 0x4C +#define TPM_CRB_CTRL_CMD_SIZE 0x58 +#define TPM_CRB_CTRL_CMD_ADDR 0x5C +#define TPM_CRB_CTRL_CMD_HADDR 0x60 +#define TPM_CRB_CTRL_RSP_SIZE 0x64 +#define TPM_CRB_CTRL_RSP_ADDR 0x68 +#define TPM_CRB_DATA_BUFFER 0x80 +#define TPMCRBBUF_LEN 0xF80 //3968 Bytes + +//#define CTRL_AREA_ADDR (uint32_t) (TPM_CRB_BASE + 0x40) +//#define DATA_BUF_ADDR (uint32_t) (TPM_CRB_BASE + 0x80) + +typedef union { + u8 _raw[4]; /* 4-byte reg */ + struct __packed { + u8 tpm_establishment : 1; + u8 loc_assigned : 1; + u8 active_locality : 3; + u8 reserved : 2; + u8 tpm_reg_valid_sts : 1; /* RO, 1=other bits are valid */ + u8 reserved1 :8; + u16 reserved2 :16; + }; +} tpm_reg_loc_state_t; + +typedef union { + uint8_t _raw[4]; + struct __packed { + uint32_t requestAccess:1; + uint32_t relinquish:1; + uint32_t seize:1; + uint32_t resetEstablishment:1; + uint32_t reserved1:28; + }; +} tpm_reg_loc_ctrl_t; + +typedef union { + uint8_t _raw[4]; + struct __packed{ + uint32_t Granted:1; + uint32_t BeenSeized:1; + uint32_t R:30; + }; +} tpm_reg_loc_sts_t; + +typedef union { + uint8_t _raw[8]; // 8-byte reg + struct __packed { + uint64_t interface_type:4; + uint64_t interface_version:4; + uint64_t interface_capability:4; + uint64_t interface_selector:4; + uint64_t rid:8; + uint64_t res:8; + uint64_t vid:16; + uint64_t did:16; + }; +} tpm_crb_interface_id_t; + +typedef union { + uint8_t _raw[4]; + struct __packed{ + uint32_t cmdReady:1; + uint32_t goIdle:1; + uint32_t Reserved:30; + }; + } tpm_reg_ctrl_request_t; + +typedef union { + uint8_t _raw[4]; + struct __packed{ + uint32_t tpmsts:1; + uint32_t tpmidle:1; + uint32_t reserved:30; + }; +} tpm_reg_ctrl_sts_t; + +typedef union { + uint8_t _raw[4]; + struct __packed{ + uint32_t start; + }; +} tpm_reg_ctrl_start_t; + +typedef union { + uint8_t _raw[4]; + struct __packed{ + uint32_t cancel; + }; +} tpm_reg_ctrl_cancel_t; + +typedef union { + uint8_t _raw[8]; + struct __packed{ + uint32_t cmdladdr; + uint32_t cmdhaddr; + }; +} tpm_reg_ctrl_cmdaddr_t; + +typedef union { + uint8_t _raw[4]; + struct __packed{ + uint32_t cmdsize; + }; +} tpm_reg_ctrl_cmdsize_t; + +typedef union { + uint8_t _raw[8]; + struct __packed{ + uint64_t rspaddr; + }; +} tpm_reg_ctrl_rspaddr_t; + +typedef union { + uint8_t _raw[4]; + struct __packed{ + uint32_t rspsize; + }; +} tpm_reg_ctrl_rspsize_t; + +typedef union { + uint8_t _raw[48]; + struct __packed { + tpm_reg_ctrl_request_t Request; + tpm_reg_ctrl_sts_t Status; + tpm_reg_ctrl_cancel_t Cancel; + tpm_reg_ctrl_start_t Start; + uint64_t R; + tpm_reg_ctrl_cmdsize_t CmdSize; + tpm_reg_ctrl_cmdaddr_t CmdAddr; + tpm_reg_ctrl_rspsize_t RspSize; + tpm_reg_ctrl_rspaddr_t RspAddr; + }; +} tpm_ctrl_area_t; + +// END OF CRB I/F + +/* + * assumes that all reg types follow above format: + * - packed + * - member named '_raw' which is array whose size is that of data to read + */ +#define read_tpm_reg(locality, reg, pdata) _read_tpm_reg(locality, reg, (pdata)->_raw, sizeof(*(pdata))) + +#define write_tpm_reg(locality, reg, pdata) _write_tpm_reg(locality, reg, (pdata)->_raw, sizeof(*(pdata))) + +static inline void _read_tpm_reg(int locality, u32 reg, u8 *_raw, size_t size) +{ + for ( size_t i = 0; i < size; i++ ) _raw[i] = readb((TPM_LOCALITY_BASE_N(locality) | reg) + i); +} + +static inline void _write_tpm_reg(int locality, u32 reg, u8 *_raw, size_t size) +{ + for ( size_t i = 0; i < size; i++ ) writeb((TPM_LOCALITY_BASE_N(locality) | reg) + i, _raw[i]); +} + + +/* + * the following inline function reversely copy the bytes from 'in' to + * 'out', the byte number to copy is given in count. + */ +#define reverse_copy(out, in, count) _reverse_copy((uint8_t *)(out), (uint8_t *)(in), count) + +static inline void _reverse_copy(uint8_t *out, uint8_t *in, uint32_t count) +{ + for ( uint32_t i = 0; i < count; i++ ) + out[i] = in[count - i - 1]; +} + +/* alg id list supported by Tboot */ +u16 tboot_alg_list[2]; + +typedef tb_hash_t tpm_digest_t; +typedef tpm_digest_t tpm_pcr_value_t; + +/* only for tpm1.2 to (un)seal */ +tpm_pcr_value_t post_launch_pcr17; +tpm_pcr_value_t post_launch_pcr18; + +struct tpm_if; + +struct tpm_if { +#define TPM12_VER_MAJOR 1 +#define TPM12_VER_MINOR 2 +#define TPM20_VER_MAJOR 2 +#define TPM20_VER_MINOR 0 + u8 major; + u8 minor; + u16 family; + + tpm_timeout_t timeout; + + u32 error; /* last reported error */ + u32 cur_loc; + + u16 banks; + u16 algs_banks[TPM_ALG_MAX_NUM]; + u16 alg_count; + u16 algs[TPM_ALG_MAX_NUM]; + + /* + * Only for version>=2. PCR extend policy. + */ +#define TB_EXTPOL_AGILE 0 +#define TB_EXTPOL_EMBEDDED 1 +#define TB_EXTPOL_FIXED 2 + u8 extpol; + u16 cur_alg; + + /* NV index to be used */ + u32 lcp_own_index; + u32 tb_policy_index; + u32 tb_err_index; + u32 sgx_svn_index; + + bool (*init)(struct tpm_if *ti); + + bool (*pcr_read)(struct tpm_if *ti, u32 locality, u32 pcr, tpm_pcr_value_t *out); + bool (*pcr_extend)(struct tpm_if *ti, u32 locality, u32 pcr, const hash_list_t *in); + bool (*pcr_reset)(struct tpm_if *ti, u32 locality, u32 pcr); + bool (*hash)(struct tpm_if *ti, u32 locality, const u8 *data, u32 data_size, hash_list_t *hl); + + bool (*nv_read)(struct tpm_if *ti, u32 locality, u32 index, u32 offset, u8 *data, u32 *data_size); + bool (*nv_write)(struct tpm_if *ti, u32 locality, u32 index, u32 offset, const u8 *data, u32 data_size); + bool (*get_nvindex_size)(struct tpm_if *ti, u32 locality, u32 index, u32 *size); + +#define TPM_NV_PER_WRITE_STCLEAR (1<<14) +#define TPM_NV_PER_WRITEDEFINE (1<<13) +#define TPM_NV_PER_WRITEALL (1<<12) +#define TPM_NV_PER_AUTHWRITE (1<<2) +#define TPM_NV_PER_OWNERWRITE (1<<1) +#define TPM_NV_PER_PPWRITE (1<<0) + bool (*get_nvindex_permission)(struct tpm_if *ti, u32 locality, u32 index, u32 *attribute); + + bool (*seal)(struct tpm_if *ti, u32 locality, u32 in_data_size, const u8 *in_data, u32 *sealed_data_size, u8 *sealed_data); + bool (*unseal)(struct tpm_if *ti, u32 locality, u32 sealed_data_size, const u8 *sealed_data, u32 *secret_size, u8 *secret); + bool (*verify_creation)(struct tpm_if *ti, u32 sealed_data_size, u8 *sealed_data); + + bool (*get_random)(struct tpm_if *ti, u32 locality, u8 *random_data, u32 *data_size); + + uint32_t (*save_state)(struct tpm_if *ti, u32 locality); + + bool (*cap_pcrs)(struct tpm_if *ti, u32 locality, int pcr); + bool (*check)(void); +}; + +struct tpm_if tpm_12_if; +struct tpm_if tpm_20_if; +struct tpm_if *g_tpm; +uint8_t g_tpm_family; + +bool tpm_validate_locality(uint32_t locality); +bool tpm_validate_locality_crb(uint32_t locality); +bool release_locality(uint32_t locality); +bool prepare_tpm(void); +bool tpm_detect(void); +void tpm_print(struct tpm_if *ti); +bool tpm_submit_cmd(u32 locality, u8 *in, u32 in_size, u8 *out, u32 *out_size); +bool tpm_submit_cmd_crb(u32 locality, u8 *in, u32 in_size, u8 *out, u32 *out_size); +bool tpm_wait_cmd_ready(uint32_t locality); +bool tpm_request_locality_crb(uint32_t locality); +bool tpm_relinquish_locality_crb(uint32_t locality); +bool txt_is_launched(void); +bool tpm_workaround_crb(void); + + +//#define TPM_UNIT_TEST 1 + +#ifdef TPM_UNIT_TEST +void tpm_unit_test(void); +#else +#define tpm_unit_test() +#endif /* TPM_UNIT_TEST */ + + +#endif /* __TPM_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/tpm_20.h b/tboot/include/tpm_20.h new file mode 100644 index 0000000..af7dab5 --- /dev/null +++ b/tboot/include/tpm_20.h @@ -0,0 +1,1503 @@ +/* + * tpm_20.h: TPM2.0-related structure + * + * Copyright (c) 2006-2013, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TPM20_H__ +#define __TPM20_H__ + +/* + * tpm2.0 structure defined in spec. + */ + +typedef struct { + u16 size; + u8 buffer[1]; +} TPM2B; + +// Table 205 -- SHA1 Hash Values +#define SHA1_DIGEST_SIZE 20 +#define SHA1_BLOCK_SIZE 64 +#define SHA1_DER_SIZE 15 +#define SHA1_DER {0x30,0x21,0x30,0x09,0x06, 0x05,0x2B,0x0E,0x03,0x02,0x1A,0x05,0x00,0x04,0x14} + +// Table 206 -- SHA256 Hash Values +#define SHA256_DIGEST_SIZE 32 +#define SHA256_BLOCK_SIZE 64 +#define SHA256_DER_SIZE 19 +#define SHA256_DER {0x30,0x31,0x30,0x0d,0x06, 0x09,0x60,0x86,0x48,0x01,0x65,0x03,0x04,0x02,0x01, 0x05,0x00,0x04,0x20} + +// Table 207 -- SHA384 Hash Values +#define SHA384_DIGEST_SIZE 48 +#define SHA384_BLOCK_SIZE 128 +#define SHA384_DER_SIZE 19 +#define SHA384_DER {0x30,0x41,0x30,0x0d,0x06, 0x09,0x60,0x86,0x48,0x01,0x65,0x03,0x04,0x02,0x02, 0x05,0x00,0x04,0x30} + + +// Table 208 -- SHA512 Hash Values +#define SHA512_DIGEST_SIZE 64 +#define SHA512_BLOCK_SIZE 128 +#define SHA512_DER_SIZE 19 +#define SHA512_DER {0x30,0x51,0x30,0x0d,0x06, \ + 0x09,0x60,0x86,0x48,0x01,0x65,0x03,0x04,0x02,0x03,\ + 0x05,0x00,0x04,0x40} + +// Table 210 -- SM3_256 Hash Values +#define SM3_256_DIGEST_SIZE 32 +#define SM3_256_BLOCK_SIZE 64 +#define SM3_256_DER_SIZE 18 +#define SM3_256_DER {0x30,0x30,0x30,0x0c,0x06, \ + 0x08,0x2A,0x81,0x1C,0x81,0x45,0x01,0x83,0x11,0x05,\ + 0x00,0x04,0x20} + +// Table 213 -- Logic Values +#define YES 1 +#define NO 0 +#define SET 1 +#define CLEAR 0 + +// Table 215 -- Implemented Algorithms +#define ALG_RSA YES // 1 +#define ALG_SHA1 YES // 1 +#define ALG_HMAC YES // 1 +#define ALG_AES YES // 1 +#define ALG_MGF1 YES // 1 +#define ALG_XOR YES // 1 +#define ALG_KEYEDHASH YES // 1 +#define ALG_SHA256 YES // 1 +#define ALG_SHA384 YES // 0 +#define ALG_SHA512 YES // 0 +#define ALG_SM3_256 YES // 1 +#define ALG_SM4 YES // 1 +#define ALG_RSASSA YES // 1 +#define ALG_RSAES YES // 1 +#define ALG_RSAPSS YES // 1 +#define ALG_OAEP YES // 1 +#define ALG_ECC YES // 1 +#define ALG_ECDH YES // 1 +#define ALG_ECDSA YES // 1 +#define ALG_ECDAA YES // 1 +#define ALG_SM2 YES // 1 +#define ALG_ECSCHNORR YES // 1 +#define ALG_SYMCIPHER YES // 1 +#define ALG_KDF1_SP800_56a YES // 1 +#define ALG_KDF2 NO // 0 +#define ALG_KDF1_SP800_108 YES // 1 +#define ALG_CTR YES // 1 +#define ALG_OFB YES // 1 +#define ALG_CBC YES // 1 +#define ALG_CFB YES // 1 +#define ALG_ECB YES // 1 + +#define HASH_COUNT (ALG_SHA1+ALG_SHA256+ALG_SM3_256+ALG_SHA384+ALG_SHA512) + +// Table 217 -- RSA Algorithm Constants +#define RSA_KEY_SIZES_BITS {1024, 2048} // {1024,2048} +#define MAX_RSA_KEY_BITS 2048 +#define MAX_RSA_KEY_BYTES ((MAX_RSA_KEY_BITS + 7) / 8) // 256 + +// Table 218 -- ECC Algorithm Constants +#define ECC_CURVES {TPM_ECC_NIST_P256,TPM_ECC_BN_P256,TPM_ECC_SM2_P256} +#define ECC_KEY_SIZES_BITS {256} +#define MAX_ECC_KEY_BITS 256 +#define MAX_ECC_KEY_BYTES ((MAX_ECC_KEY_BITS + 7) / 8) // 32 + +// Table 219 -- AES Algorithm Constants +#define AES_KEY_SIZES_BITS {128} +#define MAX_AES_KEY_BITS 128 +#define MAX_AES_BLOCK_SIZE_BYTES 16 +#define MAX_AES_KEY_BYTES ((MAX_AES_KEY_BITS + 7) / 8) // 16 + +// Table 221 -- Symmetric Algorithm Constants +#define MAX_SYM_KEY_BITS MAX_AES_KEY_BITS // 128 +#define MAX_SYM_KEY_BYTES MAX_AES_KEY_BYTES // 16 +#define MAX_SYM_BLOCK_SIZE MAX_AES_BLOCK_SIZE_BYTES // 16 + +// Table 222 -- Implementation Values +#define FIELD_UPGRADE_IMPLEMENTED NO // 0 +typedef u16 BSIZE; +#define BUFFER_ALIGNMENT 4 +#define IMPLEMENTATION_PCR 24 +#define PLATFORM_PCR 24 +#define DRTM_PCR 17 +#define NUM_LOCALITIES 5 +#define MAX_HANDLE_NUM 3 +#define MAX_ACTIVE_SESSIONS 64 +typedef u16 CONTEXT_SLOT; +typedef u64 CONTEXT_COUNTER; +#define MAX_LOADED_SESSIONS 3 +#define MAX_SESSION_NUM 3 +#define MAX_LOADED_OBJECTS 3 +#define MIN_EVICT_OBJECTS 2 +#define PCR_SELECT_MIN ((PLATFORM_PCR+7)/8) // 3 +#define PCR_SELECT_MAX ((IMPLEMENTATION_PCR+7)/8) // 3 +#define NUM_POLICY_PCR_GROUP 1 +#define NUM_AUTHVALUE_PCR_GROUP 1 +#define MAX_CONTEXT_SIZE 4000 +#define MAX_DIGEST_BUFFER 1024 +#define MAX_NV_INDEX_SIZE 1024 +#define MAX_CAP_BUFFER 1024 +#define NV_MEMORY_SIZE 16384 +#define NUM_STATIC_PCR 16 +#define MAX_ALG_LIST_SIZE 64 +#define TIMER_PRESCALE 100000 +#define PRIMARY_SEED_SIZE 32 +#define CONTEXT_ENCRYPT_ALG TPM_ALG_AES +#define CONTEXT_ENCRYPT_KEY_BITS MAX_SYM_KEY_BITS // 128 +#define CONTEXT_ENCRYPT_KEY_BYTES ((CONTEXT_ENCRYPT_KEY_BITS+7)/8) +#define CONTEXT_INTEGRITY_HASH_ALG TPM_ALG_SHA256 +#define CONTEXT_INTEGRITY_HASH_SIZE SHA256_DIGEST_SIZE // 32 +#define PROOF_SIZE CONTEXT_INTEGRITY_HASH_SIZE // 32 +#define NV_CLOCK_UPDATE_INTERVAL 12 +#define NUM_POLICY_PCR 1 +#define MAX_COMMAND_SIZE 4096 +#define MAX_RESPONSE_SIZE 4096 +#define ORDERLY_BITS 8 +#define MAX_ORDERLY_COUNT ((1 << ORDERLY_BITS) - 1) // 255 +#define ALG_ID_FIRST TPM_ALG_FIRST +#define ALG_ID_LAST TPM_ALG_LAST +#define MAX_SYM_DATA 128 +#define MAX_HASH_STATE_SIZE 512 +#define MAX_RNG_ENTROPY_SIZE 64 +#define RAM_INDEX_SPACE 512 +#define RSA_DEFAULT_PUBLIC_EXPONENT 0x00010001 +#define ENABLE_PCR_NO_INCREMENT YES // 1 + +// Table 11 -- TPM_CC Constants +typedef u32 TPM_CC; + +#define TPM_CC_FIRST (TPM_CC)(0x0000011F) +#define TPM_CC_PP_FIRST (TPM_CC)(0x0000011F) +#define TPM_CC_NV_UndefineSpaceSpecial (TPM_CC)(0x0000011F) +#define TPM_CC_EvictControl (TPM_CC)(0x00000120) +#define TPM_CC_HierarchyControl (TPM_CC)(0x00000121) +#define TPM_CC_NV_UndefineSpace (TPM_CC)(0x00000122) +#define TPM_CC_ChangeEPS (TPM_CC)(0x00000124) +#define TPM_CC_ChangePPS (TPM_CC)(0x00000125) +#define TPM_CC_Clear (TPM_CC)(0x00000126) +#define TPM_CC_ClearControl (TPM_CC)(0x00000127) +#define TPM_CC_ClockSet (TPM_CC)(0x00000128) +#define TPM_CC_HierarchyChangeAuth (TPM_CC)(0x00000129) +#define TPM_CC_NV_DefineSpace (TPM_CC)(0x0000012A) +#define TPM_CC_PCR_Allocate (TPM_CC)(0x0000012B) +#define TPM_CC_PCR_SetAuthPolicy (TPM_CC)(0x0000012C) +#define TPM_CC_PP_Commands (TPM_CC)(0x0000012D) +#define TPM_CC_SetPrimaryPolicy (TPM_CC)(0x0000012E) +#define TPM_CC_FieldUpgradeStart (TPM_CC)(0x0000012F) +#define TPM_CC_ClockRateAdjust (TPM_CC)(0x00000130) +#define TPM_CC_CreatePrimary (TPM_CC)(0x00000131) +#define TPM_CC_NV_GlobalWriteLock (TPM_CC)(0x00000132) +#define TPM_CC_PP_LAST (TPM_CC)(0x00000132) +#define TPM_CC_GetCommandAuditDigest (TPM_CC)(0x00000133) +#define TPM_CC_NV_Increment (TPM_CC)(0x00000134) +#define TPM_CC_NV_SetBits (TPM_CC)(0x00000135) +#define TPM_CC_NV_Extend (TPM_CC)(0x00000136) +#define TPM_CC_NV_Write (TPM_CC)(0x00000137) +#define TPM_CC_NV_WriteLock (TPM_CC)(0x00000138) +#define TPM_CC_DictionaryAttackLockReset (TPM_CC)(0x00000139) +#define TPM_CC_DictionaryAttackParameters (TPM_CC)(0x0000013A) +#define TPM_CC_NV_ChangeAuth (TPM_CC)(0x0000013B) +#define TPM_CC_PCR_Event (TPM_CC)(0x0000013C) +#define TPM_CC_PCR_Reset (TPM_CC)(0x0000013D) +#define TPM_CC_SequenceComplete (TPM_CC)(0x0000013E) +#define TPM_CC_SetAlgorithmSet (TPM_CC)(0x0000013F) +#define TPM_CC_SetCommandCodeAuditStatus (TPM_CC)(0x00000140) +#define TPM_CC_FieldUpgradeData (TPM_CC)(0x00000141) +#define TPM_CC_IncrementalSelfTest (TPM_CC)(0x00000142) +#define TPM_CC_SelfTest (TPM_CC)(0x00000143) +#define TPM_CC_Startup (TPM_CC)(0x00000144) +#define TPM_CC_Shutdown (TPM_CC)(0x00000145) +#define TPM_CC_StirRandom (TPM_CC)(0x00000146) +#define TPM_CC_ActivateCredential (TPM_CC)(0x00000147) +#define TPM_CC_Certify (TPM_CC)(0x00000148) +#define TPM_CC_PolicyNV (TPM_CC)(0x00000149) +#define TPM_CC_CertifyCreation (TPM_CC)(0x0000014A) +#define TPM_CC_Duplicate (TPM_CC)(0x0000014B) +#define TPM_CC_GetTime (TPM_CC)(0x0000014C) +#define TPM_CC_GetSessionAuditDigest (TPM_CC)(0x0000014D) +#define TPM_CC_NV_Read (TPM_CC)(0x0000014E) +#define TPM_CC_NV_ReadLock (TPM_CC)(0x0000014F) +#define TPM_CC_ObjectChangeAuth (TPM_CC)(0x00000150) +#define TPM_CC_PolicySecret (TPM_CC)(0x00000151) +#define TPM_CC_Rewrap (TPM_CC)(0x00000152) +#define TPM_CC_Create (TPM_CC)(0x00000153) +#define TPM_CC_ECDH_ZGen (TPM_CC)(0x00000154) +#define TPM_CC_HMAC (TPM_CC)(0x00000155) +#define TPM_CC_Import (TPM_CC)(0x00000156) +#define TPM_CC_Load (TPM_CC)(0x00000157) +#define TPM_CC_Quote (TPM_CC)(0x00000158) +#define TPM_CC_RSA_Decrypt (TPM_CC)(0x00000159) +#define TPM_CC_HMAC_Start (TPM_CC)(0x0000015B) +#define TPM_CC_SequenceUpdate (TPM_CC)(0x0000015C) +#define TPM_CC_Sign (TPM_CC)(0x0000015D) +#define TPM_CC_Unseal (TPM_CC)(0x0000015E) +#define TPM_CC_PolicySigned (TPM_CC)(0x00000160) +#define TPM_CC_ContextLoad (TPM_CC)(0x00000161) +#define TPM_CC_ContextSave (TPM_CC)(0x00000162) +#define TPM_CC_ECDH_KeyGen (TPM_CC)(0x00000163) +#define TPM_CC_EncryptDecrypt (TPM_CC)(0x00000164) +#define TPM_CC_FlushContext (TPM_CC)(0x00000165) +#define TPM_CC_LoadExternal (TPM_CC)(0x00000167) +#define TPM_CC_MakeCredential (TPM_CC)(0x00000168) +#define TPM_CC_NV_ReadPublic (TPM_CC)(0x00000169) +#define TPM_CC_PolicyAuthorize (TPM_CC)(0x0000016A) +#define TPM_CC_PolicyAuthValue (TPM_CC)(0x0000016B) +#define TPM_CC_PolicyCommandCode (TPM_CC)(0x0000016C) +#define TPM_CC_PolicyCounterTimer (TPM_CC)(0x0000016D) +#define TPM_CC_PolicyCpHash (TPM_CC)(0x0000016E) +#define TPM_CC_PolicyLocality (TPM_CC)(0x0000016F) +#define TPM_CC_PolicyNameHash (TPM_CC)(0x00000170) +#define TPM_CC_PolicyOR (TPM_CC)(0x00000171) +#define TPM_CC_PolicyTicket (TPM_CC)(0x00000172) +#define TPM_CC_ReadPublic (TPM_CC)(0x00000173) +#define TPM_CC_RSA_Encrypt (TPM_CC)(0x00000174) +#define TPM_CC_StartAuthSession (TPM_CC)(0x00000176) +#define TPM_CC_VerifySignature (TPM_CC)(0x00000177) +#define TPM_CC_ECC_Parameters (TPM_CC)(0x00000178) +#define TPM_CC_FirmwareRead (TPM_CC)(0x00000179) +#define TPM_CC_GetCapability (TPM_CC)(0x0000017A) +#define TPM_CC_GetRandom (TPM_CC)(0x0000017B) +#define TPM_CC_GetTestResult (TPM_CC)(0x0000017C) +#define TPM_CC_Hash (TPM_CC)(0x0000017D) +#define TPM_CC_PCR_Read (TPM_CC)(0x0000017E) +#define TPM_CC_PolicyPCR (TPM_CC)(0x0000017F) +#define TPM_CC_PolicyRestart (TPM_CC)(0x00000180) +#define TPM_CC_ReadClock (TPM_CC)(0x00000181) +#define TPM_CC_PCR_Extend (TPM_CC)(0x00000182) +#define TPM_CC_PCR_SetAuthValue (TPM_CC)(0x00000183) +#define TPM_CC_NV_Certify (TPM_CC)(0x00000184) +#define TPM_CC_EventSequenceComplete (TPM_CC)(0x00000185) +#define TPM_CC_HashSequenceStart (TPM_CC)(0x00000186) +#define TPM_CC_PolicyPhysicalPresence (TPM_CC)(0x00000187) +#define TPM_CC_PolicyDuplicationSelect (TPM_CC)(0x00000188) +#define TPM_CC_PolicyGetDigest (TPM_CC)(0x00000189) +#define TPM_CC_TestParms (TPM_CC)(0x0000018A) +#define TPM_CC_Commit (TPM_CC)(0x0000018B) +#define TPM_CC_PolicyPassword (TPM_CC)(0x0000018C) +#define TPM_CC_SM2_ZGen (TPM_CC)(0x0000018D) +#define TPM_CC_LAST (TPM_CC)(0x0000018D) + +// Table 15 -- TPM_RC Constants +typedef u32 TPM_RCS; // The 'safe' error codes +typedef u32 TPM_RC; + +#define TPM_RC_SUCCESS (TPM_RC)(0x000) +#define TPM_RC_BAD_TAG (TPM_RC)(0x030) +#define RC_VER1 (TPM_RC)(0x100) +#define TPM_RC_INITIALIZE (TPM_RC)(RC_VER1 + 0x000) +#define TPM_RC_FAILURE (TPM_RC)(RC_VER1 + 0x001) +#define TPM_RC_SEQUENCE (TPM_RC)(RC_VER1 + 0x003) +#define TPM_RC_PRIVATE (TPM_RC)(RC_VER1 + 0x00B) +#define TPM_RC_HMAC (TPM_RC)(RC_VER1 + 0x019) +#define TPM_RC_DISABLED (TPM_RC)(RC_VER1 + 0x020) +#define TPM_RC_EXCLUSIVE (TPM_RC)(RC_VER1 + 0x021) +#define TPM_RC_AUTH_TYPE (TPM_RC)(RC_VER1 + 0x024) +#define TPM_RC_AUTH_MISSING (TPM_RC)(RC_VER1 + 0x025) +#define TPM_RC_POLICY (TPM_RC)(RC_VER1 + 0x026) +#define TPM_RC_PCR (TPM_RC)(RC_VER1 + 0x027) +#define TPM_RC_PCR_CHANGED (TPM_RC)(RC_VER1 + 0x028) +#define TPM_RC_UPGRADE (TPM_RC)(RC_VER1 + 0x02D) +#define TPM_RC_TOO_MANY_CONTEXTS (TPM_RC)(RC_VER1 + 0x02E) +#define TPM_RC_AUTH_UNAVAILABLE (TPM_RC)(RC_VER1 + 0x02F) +#define TPM_RC_REBOOT (TPM_RC)(RC_VER1 + 0x030) +#define TPM_RC_UNBALANCED (TPM_RC)(RC_VER1 + 0x031) +#define TPM_RC_COMMAND_SIZE (TPM_RC)(RC_VER1 + 0x042) +#define TPM_RC_COMMAND_CODE (TPM_RC)(RC_VER1 + 0x043) +#define TPM_RC_AUTHSIZE (TPM_RC)(RC_VER1 + 0x044) +#define TPM_RC_AUTH_CONTEXT (TPM_RC)(RC_VER1 + 0x045) +#define TPM_RC_NV_RANGE (TPM_RC)(RC_VER1 + 0x046) +#define TPM_RC_NV_SIZE (TPM_RC)(RC_VER1 + 0x047) +#define TPM_RC_NV_LOCKED (TPM_RC)(RC_VER1 + 0x048) +#define TPM_RC_NV_AUTHORIZATION (TPM_RC)(RC_VER1 + 0x049) +#define TPM_RC_NV_UNINITIALIZED (TPM_RC)(RC_VER1 + 0x04A) +#define TPM_RC_NV_SPACE (TPM_RC)(RC_VER1 + 0x04B) +#define TPM_RC_NV_DEFINED (TPM_RC)(RC_VER1 + 0x04C) +#define TPM_RC_BAD_CONTEXT (TPM_RC)(RC_VER1 + 0x050) +#define TPM_RC_CPHASH (TPM_RC)(RC_VER1 + 0x051) +#define TPM_RC_PARENT (TPM_RC)(RC_VER1 + 0x052) +#define TPM_RC_NEEDS_TEST (TPM_RC)(RC_VER1 + 0x053) +#define TPM_RC_NO_RESULT (TPM_RC)(RC_VER1 + 0x054) +#define TPM_RC_SENSITIVE (TPM_RC)(RC_VER1 + 0x055) +#define RC_MAX_FM0 (TPM_RC)(RC_VER1 + 0x07F) +#define RC_FMT1 (TPM_RC)(0x080) +#define TPM_RC_ASYMMETRIC (TPM_RC)(RC_FMT1 + 0x001) +#define TPM_RCS_ASYMMETRIC (TPM_RCS)(RC_FMT1 + 0x001) +#define TPM_RC_ATTRIBUTES (TPM_RC)(RC_FMT1 + 0x002) +#define TPM_RCS_ATTRIBUTES (TPM_RCS)(RC_FMT1 + 0x002) +#define TPM_RC_HASH (TPM_RC)(RC_FMT1 + 0x003) +#define TPM_RCS_HASH (TPM_RCS)(RC_FMT1 + 0x003) +#define TPM_RC_VALUE (TPM_RC)(RC_FMT1 + 0x004) +#define TPM_RCS_VALUE (TPM_RCS)(RC_FMT1 + 0x004) +#define TPM_RC_HIERARCHY (TPM_RC)(RC_FMT1 + 0x005) +#define TPM_RCS_HIERARCHY (TPM_RCS)(RC_FMT1 + 0x005) +#define TPM_RC_KEY_SIZE (TPM_RC)(RC_FMT1 + 0x007) +#define TPM_RCS_KEY_SIZE (TPM_RCS)(RC_FMT1 + 0x007) +#define TPM_RC_MGF (TPM_RC)(RC_FMT1 + 0x008) +#define TPM_RCS_MGF (TPM_RCS)(RC_FMT1 + 0x008) +#define TPM_RC_MODE (TPM_RC)(RC_FMT1 + 0x009) +#define TPM_RCS_MODE (TPM_RCS)(RC_FMT1 + 0x009) +#define TPM_RC_TYPE (TPM_RC)(RC_FMT1 + 0x00A) +#define TPM_RCS_TYPE (TPM_RCS)(RC_FMT1 + 0x00A) +#define TPM_RC_HANDLE (TPM_RC)(RC_FMT1 + 0x00B) +#define TPM_RCS_HANDLE (TPM_RCS)(RC_FMT1 + 0x00B) +#define TPM_RC_KDF (TPM_RC)(RC_FMT1 + 0x00C) +#define TPM_RCS_KDF (TPM_RCS)(RC_FMT1 + 0x00C) +#define TPM_RC_RANGE (TPM_RC)(RC_FMT1 + 0x00D) +#define TPM_RCS_RANGE (TPM_RCS)(RC_FMT1 + 0x00D) +#define TPM_RC_AUTH_FAIL (TPM_RC)(RC_FMT1 + 0x00E) +#define TPM_RCS_AUTH_FAIL (TPM_RCS)(RC_FMT1 + 0x00E) +#define TPM_RC_NONCE (TPM_RC)(RC_FMT1 + 0x00F) +#define TPM_RCS_NONCE (TPM_RCS)(RC_FMT1 + 0x00F) +#define TPM_RC_PP (TPM_RC)(RC_FMT1 + 0x010) +#define TPM_RCS_PP (TPM_RCS)(RC_FMT1 + 0x010) +#define TPM_RC_SCHEME (TPM_RC)(RC_FMT1 + 0x012) +#define TPM_RCS_SCHEME (TPM_RCS)(RC_FMT1 + 0x012) +#define TPM_RC_SIZE (TPM_RC)(RC_FMT1 + 0x015) +#define TPM_RCS_SIZE (TPM_RCS)(RC_FMT1 + 0x015) +#define TPM_RC_SYMMETRIC (TPM_RC)(RC_FMT1 + 0x016) +#define TPM_RCS_SYMMETRIC (TPM_RCS)(RC_FMT1 + 0x016) +#define TPM_RC_TAG (TPM_RC)(RC_FMT1 + 0x017) +#define TPM_RCS_TAG (TPM_RCS)(RC_FMT1 + 0x017) +#define TPM_RC_SELECTOR (TPM_RC)(RC_FMT1 + 0x018) +#define TPM_RCS_SELECTOR (TPM_RCS)(RC_FMT1 + 0x018) +#define TPM_RC_INSUFFICIENT (TPM_RC)(RC_FMT1 + 0x01A) +#define TPM_RCS_INSUFFICIENT (TPM_RCS)(RC_FMT1 + 0x01A) +#define TPM_RC_SIGNATURE (TPM_RC)(RC_FMT1 + 0x01B) +#define TPM_RCS_SIGNATURE (TPM_RCS)(RC_FMT1 + 0x01B) +#define TPM_RC_KEY (TPM_RC)(RC_FMT1 + 0x01C) +#define TPM_RCS_KEY (TPM_RCS)(RC_FMT1 + 0x01C) +#define TPM_RC_POLICY_FAIL (TPM_RC)(RC_FMT1 + 0x01D) +#define TPM_RCS_POLICY_FAIL (TPM_RCS)(RC_FMT1 + 0x01D) +#define TPM_RC_INTEGRITY (TPM_RC)(RC_FMT1 + 0x01F) +#define TPM_RCS_INTEGRITY (TPM_RCS)(RC_FMT1 + 0x01F) +#define TPM_RC_TICKET (TPM_RC)(RC_FMT1 + 0x020) +#define TPM_RCS_TICKET (TPM_RCS)(RC_FMT1 + 0x020) +#define TPM_RC_RESERVED_BITS (TPM_RC)(RC_FMT1 + 0x021) +#define TPM_RCS_RESERVED_BITS (TPM_RCS)(RC_FMT1 + 0x021) +#define TPM_RC_BAD_AUTH (TPM_RC)(RC_FMT1 + 0x022) +#define TPM_RCS_BAD_AUTH (TPM_RCS)(RC_FMT1 + 0x022) +#define TPM_RC_EXPIRED (TPM_RC)(RC_FMT1 + 0x023) +#define TPM_RCS_EXPIRED (TPM_RCS)(RC_FMT1 + 0x023) +#define TPM_RC_POLICY_CC (TPM_RC)(RC_FMT1 + 0x024 ) +#define TPM_RCS_POLICY_CC (TPM_RCS)(RC_FMT1 + 0x024 ) +#define TPM_RC_BINDING (TPM_RC)(RC_FMT1 + 0x025) +#define TPM_RCS_BINDING (TPM_RCS)(RC_FMT1 + 0x025) +#define TPM_RC_CURVE (TPM_RC)(RC_FMT1 + 0x026) +#define TPM_RCS_CURVE (TPM_RCS)(RC_FMT1 + 0x026) +#define TPM_RC_ECC_POINT (TPM_RC)(RC_FMT1 + 0x027) +#define TPM_RCS_ECC_POINT (TPM_RCS)(RC_FMT1 + 0x027) +#define RC_WARN (TPM_RC)(0x900) +#define TPM_RC_CONTEXT_GAP (TPM_RC)(RC_WARN + 0x001) +#define TPM_RC_OBJECT_MEMORY (TPM_RC)(RC_WARN + 0x002) +#define TPM_RC_SESSION_MEMORY (TPM_RC)(RC_WARN + 0x003) +#define TPM_RC_MEMORY (TPM_RC)(RC_WARN + 0x004) +#define TPM_RC_SESSION_HANDLES (TPM_RC)(RC_WARN + 0x005) +#define TPM_RC_OBJECT_HANDLES (TPM_RC)(RC_WARN + 0x006) +#define TPM_RC_LOCALITY (TPM_RC)(RC_WARN + 0x007) +#define TPM_RC_YIELDED (TPM_RC)(RC_WARN + 0x008) +#define TPM_RC_CANCELLED (TPM_RC)(RC_WARN + 0x009) +#define TPM_RC_TESTING (TPM_RC)(RC_WARN + 0x00A) +#define TPM_RC_REFERENCE_H0 (TPM_RC)(RC_WARN + 0x010) +#define TPM_RC_REFERENCE_H1 (TPM_RC)(RC_WARN + 0x011) +#define TPM_RC_REFERENCE_H2 (TPM_RC)(RC_WARN + 0x012) +#define TPM_RC_REFERENCE_H3 (TPM_RC)(RC_WARN + 0x013) +#define TPM_RC_REFERENCE_H4 (TPM_RC)(RC_WARN + 0x014) +#define TPM_RC_REFERENCE_H5 (TPM_RC)(RC_WARN + 0x015) +#define TPM_RC_REFERENCE_H6 (TPM_RC)(RC_WARN + 0x016) +#define TPM_RC_REFERENCE_S0 (TPM_RC)(RC_WARN + 0x018) +#define TPM_RC_REFERENCE_S1 (TPM_RC)(RC_WARN + 0x019) +#define TPM_RC_REFERENCE_S2 (TPM_RC)(RC_WARN + 0x01A) +#define TPM_RC_REFERENCE_S3 (TPM_RC)(RC_WARN + 0x01B) +#define TPM_RC_REFERENCE_S4 (TPM_RC)(RC_WARN + 0x01C) +#define TPM_RC_REFERENCE_S5 (TPM_RC)(RC_WARN + 0x01D) +#define TPM_RC_REFERENCE_S6 (TPM_RC)(RC_WARN + 0x01E) +#define TPM_RC_NV_RATE (TPM_RC)(RC_WARN + 0x020) +#define TPM_RC_LOCKOUT (TPM_RC)(RC_WARN + 0x021) +#define TPM_RC_RETRY (TPM_RC)(RC_WARN + 0x022) +#define TPM_RC_NV_UNAVAILABLE (TPM_RC)(RC_WARN + 0x023) +#define TPM_RC_NOT_USED (TPM_RC)(RC_WARN + 0x7F) +#define TPM_RC_H (TPM_RC)(0x000) +#define TPM_RC_P (TPM_RC)(0x040) +#define TPM_RC_S (TPM_RC)(0x800) +#define TPM_RC_1 (TPM_RC)(0x100) +#define TPM_RC_2 (TPM_RC)(0x200) +#define TPM_RC_3 (TPM_RC)(0x300) +#define TPM_RC_4 (TPM_RC)(0x400) +#define TPM_RC_5 (TPM_RC)(0x500) +#define TPM_RC_6 (TPM_RC)(0x600) +#define TPM_RC_7 (TPM_RC)(0x700) +#define TPM_RC_8 (TPM_RC)(0x800) +#define TPM_RC_9 (TPM_RC)(0x900) +#define TPM_RC_A (TPM_RC)(0xA00) +#define TPM_RC_B (TPM_RC)(0xB00) +#define TPM_RC_C (TPM_RC)(0xC00) +#define TPM_RC_D (TPM_RC)(0xD00) +#define TPM_RC_E (TPM_RC)(0xE00) +#define TPM_RC_F (TPM_RC)(0xF00) +#define TPM_RC_N_MASK (TPM_RC)(0xF00) + +// Table 18 -- TPM_ST Constants +typedef u16 TPM_ST; + +#define TPM_ST_RSP_COMMAND (TPM_ST)(0x00C4) +#define TPM_ST_NULL (TPM_ST)(0X8000) +#define TPM_ST_NO_SESSIONS (TPM_ST)(0x8001) +#define TPM_ST_SESSIONS (TPM_ST)(0x8002) +#define TPM_ST_ATTEST_NV (TPM_ST)(0x8014) +#define TPM_ST_ATTEST_COMMAND_AUDIT (TPM_ST)(0x8015) +#define TPM_ST_ATTEST_SESSION_AUDIT (TPM_ST)(0x8016) +#define TPM_ST_ATTEST_CERTIFY (TPM_ST)(0x8017) +#define TPM_ST_ATTEST_QUOTE (TPM_ST)(0x8018) +#define TPM_ST_ATTEST_TIME (TPM_ST)(0x8019) +#define TPM_ST_ATTEST_CREATION (TPM_ST)(0x801A) +#define TPM_ST_CREATION (TPM_ST)(0x8021) +#define TPM_ST_VERIFIED (TPM_ST)(0x8022) +#define TPM_ST_AUTH_SECRET (TPM_ST)(0x8023) +#define TPM_ST_HASHCHECK (TPM_ST)(0x8024) +#define TPM_ST_AUTH_SIGNED (TPM_ST)(0x8025) +#define TPM_ST_FU_MANIFEST (TPM_ST)(0x8029) + +// Table 19 -- TPM_SU Constants +typedef u16 TPM_SU; + +#define TPM_SU_CLEAR (TPM_SU)(0x0000) +#define TPM_SU_STATE (TPM_SU)(0x0001) + +// Table 21 -- TPM_CAP Constants +typedef u32 TPM_CAP; + +#define TPM_CAP_FIRST (TPM_CAP)(0x00000000) +#define TPM_CAP_ALGS (TPM_CAP)(0x00000000) +#define TPM_CAP_HANDLES (TPM_CAP)(0x00000001) +#define TPM_CAP_COMMANDS (TPM_CAP)(0x00000002) +#define TPM_CAP_PP_COMMANDS (TPM_CAP)(0x00000003) +#define TPM_CAP_AUDIT_COMMANDS (TPM_CAP)(0x00000004) +#define TPM_CAP_PCRS (TPM_CAP)(0x00000005) +#define TPM_CAP_TPM_PROPERTIES (TPM_CAP)(0x00000006) +#define TPM_CAP_PCR_PROPERTIES (TPM_CAP)(0x00000007) +#define TPM_CAP_ECC_CURVES (TPM_CAP)(0x00000008) +#define TPM_CAP_LAST (TPM_CAP)(0x00000008) +#define TPM_CAP_VENDOR_PROPERTY (TPM_CAP)(0x00000100) + +// Table 25 -- Handles Types +typedef u32 TPM_HANDLE; +typedef u8 TPM_HT; + +#define TPM_HT_PCR (TPM_HT)(0x00) +#define TPM_HT_NV_INDEX (TPM_HT)(0x01) +#define TPM_HT_HMAC_SESSION (TPM_HT)(0x02) +#define TPM_HT_LOADED_SESSION (TPM_HT)(0x02) +#define TPM_HT_POLICY_SESSION (TPM_HT)(0x03) +#define TPM_HT_ACTIVE_SESSION (TPM_HT)(0x03) +#define TPM_HT_PERMANENT (TPM_HT)(0x40) +#define TPM_HT_TRANSIENT (TPM_HT)(0x80) +#define TPM_HT_PERSISTENT (TPM_HT)(0x81) + +// Table 27 -- TPM_RH Constants +typedef u32 TPM_RH; + +#define TPM_RH_FIRST (TPM_RH)(0x40000000) +#define TPM_RH_SRK (TPM_RH)(0x40000000) +#define TPM_RH_OWNER (TPM_RH)(0x40000001) +#define TPM_RH_REVOKE (TPM_RH)(0x40000002) +#define TPM_RH_TRANSPORT (TPM_RH)(0x40000003) +#define TPM_RH_OPERATOR (TPM_RH)(0x40000004) +#define TPM_RH_ADMIN (TPM_RH)(0x40000005) +#define TPM_RH_EK (TPM_RH)(0x40000006) +#define TPM_RH_NULL (TPM_RH)(0x40000007) +#define TPM_RH_UNASSIGNED (TPM_RH)(0x40000008) +#define TPM_RS_PW (TPM_RH)(0x40000009) +#define TPM_RH_LOCKOUT (TPM_RH)(0x4000000A) +#define TPM_RH_ENDORSEMENT (TPM_RH)(0x4000000B) +#define TPM_RH_PLATFORM (TPM_RH)(0x4000000C) +#define TPM_RH_LAST (TPM_RH)(0x4000000C) + +// Table 29 -- TPMA_ALGORITHM Bits +typedef struct { + unsigned int asymmetric : 1; + unsigned int symmetric : 1; + unsigned int hash : 1; + unsigned int object : 1; + unsigned int reserved5 : 4; + unsigned int signing : 1; + unsigned int encrypting : 1; + unsigned int method : 1; + unsigned int reserved9 : 21; +} TPMA_ALGORITHM ; + +// Table 30 -- TPMA_OBJECT Bits +typedef struct { + unsigned int reserved1 : 1; + unsigned int fixedTPM : 1; + unsigned int stClear : 1; + unsigned int reserved4 : 1; + unsigned int fixedParent : 1; + unsigned int sensitiveDataOrigin : 1; + unsigned int userWithAuth : 1; + unsigned int adminWithPolicy : 1; + unsigned int reserved9 : 2; + unsigned int noDA : 1; + unsigned int encryptedDuplication : 1; + unsigned int reserved12 : 4; + unsigned int restricted : 1; // Start of 2nd dword + unsigned int decrypt : 1; + unsigned int sign : 1; + unsigned int reserved16 : 13; +} TPMA_OBJECT ; + +// Table 31 -- TPMA_SESSION Bits +typedef struct { + unsigned int continueSession : 1; + unsigned int auditExclusive : 1; + unsigned int auditReset : 1; + unsigned int reserved4 : 2; + unsigned int decrypt : 1; + unsigned int encrypt : 1; + unsigned int audit : 1; +} TPMA_SESSION; + +// Table 32 -- TPMA_LOCALITY Bits +typedef struct { + unsigned int TPM_LOC_ZERO : 1; + unsigned int TPM_LOC_ONE : 1; + unsigned int TPM_LOC_TWO : 1; + unsigned int TPM_LOC_THREE : 1; + unsigned int TPM_LOC_FOUR : 1; + unsigned int reserved6 : 3; +} TPMA_LOCALITY; + +// Table 66 -- TPMU_HA Union +typedef union { +#ifdef TPM_ALG_SHA1 + u8 sha1[SHA1_DIGEST_SIZE]; +#endif +#ifdef TPM_ALG_SHA256 + u8 sha256[SHA256_DIGEST_SIZE]; +#endif +#ifdef TPM_ALG_SM3_256 + u8 sm3_256[SM3_256_DIGEST_SIZE]; +#endif +#ifdef TPM_ALG_SHA384 + u8 sha384[SHA384_DIGEST_SIZE]; +#endif +#ifdef TPM_ALG_SHA512 + u8 sha512[SHA512_DIGEST_SIZE]; +#endif +} TPMU_HA ; + +// Table 67 -- TPMT_HA Structure +typedef struct { + u16 hash_alg; + TPMU_HA digest; +} TPMT_HA; + +// Table 68 -- TPM2B_DIGEST Structure +typedef struct { + u16 size; + u8 buffer[sizeof(TPMU_HA)]; +} DIGEST_2B; + +typedef union { + DIGEST_2B t; + TPM2B b; +} TPM2B_DIGEST; + +// Table 69 -- TPM2B_DATA Structure +typedef struct { + u16 size; + u8 buffer[sizeof(TPMT_HA)]; +} DATA_2B; + +typedef union { + DATA_2B t; + TPM2B b; +} TPM2B_DATA; + +// Table 70 -- TPM2B_NONCE Types +typedef TPM2B_DIGEST TPM2B_NONCE; + +// Table 71 -- TPM2B_AUTH Types +typedef TPM2B_DIGEST TPM2B_AUTH; + +// Table 73 -- TPM2B_EVENT Structure +typedef struct { + u16 size; + u8 buffer[1024]; +} EVENT_2B; + +typedef union { + EVENT_2B t; + TPM2B b; +} TPM2B_EVENT; + +// Table 74 -- TPM2B_MAX_BUFFER Structure +typedef struct { + u16 size; + u8 buffer[MAX_DIGEST_BUFFER]; +} MAX_BUFFER_2B; + +typedef union { + MAX_BUFFER_2B t; + TPM2B b; +} TPM2B_MAX_BUFFER; + +// Table 75 -- TPM2B_MAX_NV_BUFFER Structure +typedef struct { + u16 size; + u8 buffer[MAX_NV_INDEX_SIZE]; +} MAX_NV_BUFFER_2B; + +typedef union { + MAX_NV_BUFFER_2B t; + TPM2B b; +} TPM2B_MAX_NV_BUFFER; + +// Table 79 -- TPMU_NAME Structure +typedef union { + TPMT_HA digest; + u32 handle; +} TPMU_NAME ; + +// Table 79 -- TPM2B_NAME Structure +typedef struct { + u16 size; + u8 name[sizeof(TPMU_NAME)]; +} NAME_2B; + +typedef union { + NAME_2B t; + TPM2B b; +} TPM2B_NAME; + +// Table 80 -- TPMS_PCR_SELECTION Structure +typedef struct { + u16 hash; + u8 size_of_select; + u8 pcr_select[PCR_SELECT_MAX]; +} TPMS_PCR_SELECTION; + +// Table 84 -- TPMT_TK_CREATION Structure +typedef struct { + u16 tag; + u32 hierarchy; + TPM2B_DIGEST digest; +} TPMT_TK_CREATION; + +// Table 86 -- TPMT_TK_HASHCHECK Structure +typedef struct { + u16 tag; + u32 hierarchy; + TPM2B_DIGEST digest; +} TPMT_TK_HASHCHECK; + +// Table 88 -- TPMS_ALG_PROPERTY Structure +typedef struct { + u16 alg; + TPMA_ALGORITHM alg_pro; +} TPMS_ALG_PROPERTY; + +// Table 95 -- TPML_DIGEST Structure +typedef struct { + u32 count; + TPM2B_DIGEST digests[8]; +} TPML_DIGEST; + +// Table 96 -- TPML_DIGEST_VALUES Structure +typedef struct { + u32 count; + TPMT_HA digests[HASH_COUNT]; +} TPML_DIGEST_VALUES; + +// Table 98 -- TPML_PCR_SELECTION Structure +typedef struct { + u32 count; + TPMS_PCR_SELECTION selections[HASH_COUNT]; +} TPML_PCR_SELECTION; + +#define MAX_CAP_DATA (MAX_CAP_BUFFER-sizeof(u32)-sizeof(u32)) +#define MAX_CAP_ALGS (MAX_CAP_DATA/sizeof(TPMS_ALG_PROPERTY)) +// Table 99 -- TPML_ALG_PROPERTY Structure +typedef struct { + u32 count; + TPMS_ALG_PROPERTY alg_pros[MAX_CAP_ALGS]; +} TPML_ALG_PROPERTY; + +// Table 103 -- TPMU_CAPABILITIES Union +typedef union { + TPML_ALG_PROPERTY algs; +} TPMU_CAPABILITIES; + +// Table 104 -- TPMS_CAPABILITY_DATA Structure +typedef struct { + u32 capability; + TPMU_CAPABILITIES data; +} TPMS_CAPABILITY_DATA; + +// Table 122 -- TPMU_SYM_KEY_BITS Union +typedef union { +#ifdef TPM_ALG_AES + u16 aes; +#endif +#ifdef TPM_ALG_SM4 + u16 sm4; +#endif + u16 sym; +#ifdef TPM_ALG_XOR + u16 xor; +#endif +} TPMU_SYM_KEY_BITS ; + +// Table 122 -- TPMU_SYM_MODE Union +typedef union { +#ifdef TPM_ALG_AES + u16 aes; +#endif +#ifdef TPM_ALG_SM4 + u16 sm4; +#endif + u16 sym; +} TPMU_SYM_MODE ; + +// Table 126 -- TPMT_SYM_DEF_OBJECT Structure +typedef struct { + u16 alg; + TPMU_SYM_KEY_BITS key_bits; + TPMU_SYM_MODE mode; +} TPMT_SYM_DEF_OBJECT; + +// Table 126 -- TPM2B_SYM_KEY Structure +typedef struct { + u16 size; + u8 buffer[MAX_SYM_KEY_BYTES]; +} SYM_KEY_2B; + +typedef union { + SYM_KEY_2B t; + TPM2B b; +} TPM2B_SYM_KEY; + +// Table 129 -- TPM2B_SENSITIVE_DATA Structure +typedef struct { + u16 size; + u8 buffer[MAX_SYM_DATA]; +} SENSITIVE_DATA_2B; + +typedef union { + SENSITIVE_DATA_2B t; + TPM2B b; +} TPM2B_SENSITIVE_DATA; + +// Table 130 -- TPMS_SENSITIVE_CREATE Structure +typedef struct { + TPM2B_AUTH user_auth; + TPM2B_SENSITIVE_DATA data; +} TPMS_SENSITIVE_CREATE; + +// Table 131 -- TPM2B_SENSITIVE_CREATE Structure +typedef struct { + u16 size; + TPMS_SENSITIVE_CREATE sensitive; +} SENSITIVE_CREATE_2B; + +typedef union { + SENSITIVE_CREATE_2B t; + TPM2B b; +} TPM2B_SENSITIVE_CREATE; + +// Table 132 -- TPMS_SCHEME_SIGHASH Structure +typedef struct { + u16 hash_alg; +} TPMS_SCHEME_SIGHASH; + +// Table 134 -- HMAC_SIG_SCHEME Types +typedef TPMS_SCHEME_SIGHASH TPMS_SCHEME_HMAC; + +// Table 135 -- TPMS_SCHEME_XOR Structure +typedef struct { + u16 hash_alg; + u16 kdf; +} TPMS_SCHEME_XOR; + +// Table 136 -- TPMU_SCHEME_KEYEDHASH Union +typedef union { +#ifdef TPM_ALG_HMAC + TPMS_SCHEME_HMAC hmac; +#endif +#ifdef TPM_ALG_XOR + TPMS_SCHEME_XOR xor; +#endif + +} TPMU_SCHEME_KEYEDHASH; + +// Table 137 -- TPMT_KEYEDHASH_SCHEME Structure +typedef struct { + u16 scheme; + TPMU_SCHEME_KEYEDHASH details; +} TPMT_KEYEDHASH_SCHEME; + +// Table 138 -- RSA_SIG_SCHEMES Types +typedef TPMS_SCHEME_SIGHASH TPMS_SCHEME_RSASSA; +typedef TPMS_SCHEME_SIGHASH TPMS_SCHEME_RSAPSS; + +// Table 139 -- ECC_SIG_SCHEMES Types +typedef TPMS_SCHEME_SIGHASH TPMS_SCHEME_ECDSA; +typedef TPMS_SCHEME_SIGHASH TPMS_SCHEME_SM2; +typedef TPMS_SCHEME_SIGHASH TPMS_SCHEME_ECSCHNORR; + +// Table 140 -- TPMS_SCHEME_ECDAA Structure +typedef struct { + u16 hash_alg; + u16 count; +} TPMS_SCHEME_ECDAA; + +// Table 141 -- TPMU_SIG_SCHEME Union +typedef union { +#ifdef TPM_ALG_RSASSA + TPMS_SCHEME_RSASSA rsassa; +#endif +#ifdef TPM_ALG_RSAPSS + TPMS_SCHEME_RSAPSS rsapss; +#endif +#ifdef TPM_ALG_ECDSA + TPMS_SCHEME_ECDSA ecdsa; +#endif +#ifdef TPM_ALG_SM2 + TPMS_SCHEME_SM2 sm2; +#endif +#ifdef TPM_ALG_ECDAA + TPMS_SCHEME_ECDAA ecdaa; +#endif +#ifdef TPM_ALG_ECSCHNORR + TPMS_SCHEME_ECSCHNORR ec_schnorr; +#endif +#ifdef TPM_ALG_HMAC + TPMS_SCHEME_HMAC hmac; +#endif + TPMS_SCHEME_SIGHASH any; + +} TPMU_SIG_SCHEME ; + +// Table 143 -- TPMS_SCHEME_OAEP Structure +typedef struct { + u16 hash_alg; +} TPMS_SCHEME_OAEP; + +// Table 145 -- TPMS_SCHEME_MGF1 Structure +typedef struct { + u16 hash_alg; +} TPMS_SCHEME_MGF1; + +// Table 146 -- TPMS_SCHEME_KDF1_SP800_56a Structure +typedef struct { + u16 hash_alg; +} TPMS_SCHEME_KDF1_SP800_56a; + +// Table 147 -- TPMS_SCHEME_KDF2 Structure +typedef struct { + u16 hash_alg; +} TPMS_SCHEME_KDF2; + +// Table 148 -- TPMS_SCHEME_KDF1_SP800_108 Structure +typedef struct { + u16 hash_alg; +} TPMS_SCHEME_KDF1_SP800_108; + +// Table 149 -- TPMU_KDF_SCHEME Union +typedef union { +#ifdef TPM_ALG_MGF1 + TPMS_SCHEME_MGF1 mgf1; +#endif +#ifdef TPM_ALG_KDF1_SP800_56a + TPMS_SCHEME_KDF1_SP800_56a kdf1_SP800_56a; +#endif +#ifdef TPM_ALG_KDF2 + TPMS_SCHEME_KDF2 kdf2; +#endif +#ifdef TPM_ALG_KDF1_SP800_108 + TPMS_SCHEME_KDF1_SP800_108 kdf1_sp800_108; +#endif +} TPMU_KDF_SCHEME ; + +// Table 150 -- TPMT_KDF_SCHEME Structure +typedef struct { + u16 scheme; + TPMU_KDF_SCHEME details; +} TPMT_KDF_SCHEME; + +// Table 152 -- TPMU_ASYM_SCHEME Union +typedef union { +#ifdef TPM_ALG_RSASSA + TPMS_SCHEME_RSASSA rsassa; +#endif +#ifdef TPM_ALG_RSAPSS + TPMS_SCHEME_RSAPSS rsapss; +#endif +#ifdef TPM_ALG_OAEP + TPMS_SCHEME_OAEP oaep; +#endif +#ifdef TPM_ALG_ECDSA + TPMS_SCHEME_ECDSA ecdsa; +#endif +#ifdef TPM_ALG_SM2 + TPMS_SCHEME_SM2 sm2; +#endif +#ifdef TPM_ALG_ECDAA + TPMS_SCHEME_ECDAA ecdaa; +#endif +#ifdef TPM_ALG_ECSCHNORR + TPMS_SCHEME_ECSCHNORR ec_schnorr; +#endif + TPMS_SCHEME_SIGHASH any; + +} TPMU_ASYM_SCHEME; + +// Table 153 -- TPMT_ASYM_SCHEME Structure <> +typedef struct { + u16 scheme; + TPMU_ASYM_SCHEME details; +} TPMT_ASYM_SCHEME; + +// Table 155 -- TPMT_RSA_SCHEME Structure +typedef struct { + u16 scheme; + TPMU_ASYM_SCHEME details; +} TPMT_RSA_SCHEME; + +// Table 158 -- TPM2B_PUBLIC_KEY_RSA Structure +typedef struct { + u16 size; + u8 buffer[MAX_RSA_KEY_BYTES]; +} PUBLIC_KEY_RSA_2B; + +typedef union { + PUBLIC_KEY_RSA_2B t; + TPM2B b; +} TPM2B_PUBLIC_KEY_RSA; + +// Table 160 -- TPM2B_PRIVATE_KEY_RSA Structure +typedef struct { + u16 size; + u8 buffer[MAX_RSA_KEY_BYTES/2]; +} PRIVATE_KEY_RSA_2B; + +typedef union { + PRIVATE_KEY_RSA_2B t; + TPM2B b; +} TPM2B_PRIVATE_KEY_RSA; + +// Table 161 -- TPM2B_ECC_PARAMETER Structure +typedef struct { + u16 size; + u8 buffer[MAX_ECC_KEY_BYTES]; +} ECC_PARAMETER_2B; + +typedef union { + ECC_PARAMETER_2B t; + TPM2B b; +} TPM2B_ECC_PARAMETER; + +// Table 162 -- TPMS_ECC_POINT Structure +typedef struct { + TPM2B_ECC_PARAMETER x; + TPM2B_ECC_PARAMETER y; +} TPMS_ECC_POINT; + +// Table 166 -- TPMT_ECC_SCHEME Structure +typedef struct { + u16 scheme; + TPMU_SIG_SCHEME details; +} TPMT_ECC_SCHEME; + +// Table 176 -- TPMU_PUBLIC_ID Union +typedef union { +#ifdef TPM_ALG_KEYEDHASH + TPM2B_DIGEST keyed_hash; +#endif +#ifdef TPM_ALG_SYMCIPHER + TPM2B_DIGEST sym; +#endif +#ifdef TPM_ALG_RSA + TPM2B_PUBLIC_KEY_RSA rsa; +#endif +#ifdef TPM_ALG_ECC + TPMS_ECC_POINT ecc; +#endif +} TPMU_PUBLIC_ID; + +// Table 177 -- TPMS_KEYEDHASH_PARMS Structure +typedef struct { + TPMT_KEYEDHASH_SCHEME scheme; +} TPMS_KEYEDHASH_PARMS; + +// Table 178 -- TPMS_ASYM_PARMS Structure +typedef struct { + TPMT_SYM_DEF_OBJECT symmetric; + TPMT_ASYM_SCHEME scheme; +} TPMS_ASYM_PARMS; + +// Table 179 -- TPMS_RSA_PARMS Structure +typedef struct { + TPMT_SYM_DEF_OBJECT symmetric; + TPMT_RSA_SCHEME scheme; + u16 key_bits; + u32 exponent; +} TPMS_RSA_PARMS; + +// Table 180 -- TPMS_ECC_PARMS Structure +typedef struct { + TPMT_SYM_DEF_OBJECT symmetric; + TPMT_ECC_SCHEME scheme; + u16 curve_id; + TPMT_KDF_SCHEME kdf; +} TPMS_ECC_PARMS; + +// Table 181 -- TPMU_PUBLIC_PARMS Union +typedef union { +#ifdef TPM_ALG_KEYEDHASH + TPMS_KEYEDHASH_PARMS keyed_hash; +#endif +#ifdef TPM_ALG_SYMCIPHER + TPMT_SYM_DEF_OBJECT sym; +#endif +#ifdef TPM_ALG_RSA + TPMS_RSA_PARMS rsa; +#endif +#ifdef TPM_ALG_ECC + TPMS_ECC_PARMS ecc; +#endif + TPMS_ASYM_PARMS asym; + +} TPMU_PUBLIC_PARMS; + +// Table 184 -- TPMT_PUBLIC Structure +typedef struct { + u16 type; + u16 name_alg; + TPMA_OBJECT object_attr; + TPM2B_DIGEST auth_policy; + TPMU_PUBLIC_PARMS param; + TPMU_PUBLIC_ID unique; +} TPMT_PUBLIC; + +// Table 185 -- TPM2B_PUBLIC Structure +typedef struct { + u16 size; + TPMT_PUBLIC public_area; +} PUBLIC_2B; + +typedef union { + PUBLIC_2B t; + TPM2B b; +} TPM2B_PUBLIC; + +// Table 186 -- TPMU_SENSITIVE_COMPOSITE Union +typedef union { +#ifdef TPM_ALG_RSA + TPM2B_PRIVATE_KEY_RSA rsa; +#endif +#ifdef TPM_ALG_ECC + TPM2B_ECC_PARAMETER ecc; +#endif +#ifdef TPM_ALG_KEYEDHASH + TPM2B_SENSITIVE_DATA bits; +#endif +#ifdef TPM_ALG_SYMCIPHER + TPM2B_SYM_KEY sym; +#endif + TPM2B_SENSITIVE_DATA any; + +} TPMU_SENSITIVE_COMPOSITE ; + +// Table 187 -- TPMT_SENSITIVE Structure +typedef struct { + u16 type; + TPM2B_AUTH auth_value; + TPM2B_DIGEST seedValue; + TPMU_SENSITIVE_COMPOSITE sensitive; +} TPMT_SENSITIVE; + +// Table 189 -- _PRIVATE Structure <> +typedef struct { + TPM2B_DIGEST integrity_outer; + TPM2B_DIGEST integrity_inner; + TPMT_SENSITIVE sensitive; +} _PRIVATE; + +// Table 190 -- TPM2B_PRIVATE Structure +typedef struct { + u16 size; + u8 buffer[sizeof(_PRIVATE)]; +} PRIVATE_2B; + +typedef union { + PRIVATE_2B t; + TPM2B b; +} TPM2B_PRIVATE; + +// Table 195 -- TPMA_NV Bits +typedef struct { + unsigned int TPMA_NV_PPWRITE : 1; + unsigned int TPMA_NV_OWNERWRITE : 1; + unsigned int TPMA_NV_AUTHWRITE : 1; + unsigned int TPMA_NV_POLICYWRITE : 1; + unsigned int TPMA_NV_COUNTER : 1; + unsigned int TPMA_NV_BITS : 1; + unsigned int TPMA_NV_EXTEND : 1; + unsigned int reserved8 : 3; + unsigned int TPMA_NV_POLICY_DELETE : 1; + unsigned int TPMA_NV_WRITELOCKED : 1; + unsigned int TPMA_NV_WRITEALL : 1; + unsigned int TPMA_NV_WRITEDEFINE : 1; + unsigned int TPMA_NV_WRITE_STCLEAR : 1; + unsigned int TPMA_NV_GLOBALLOCK : 1; + unsigned int TPMA_NV_PPREAD : 1; + unsigned int TPMA_NV_OWNERREAD : 1; + unsigned int TPMA_NV_AUTHREAD : 1; + unsigned int TPMA_NV_POLICYREAD : 1; + unsigned int reserved19 : 5; + unsigned int TPMA_NV_NO_DA : 1; + unsigned int TPMA_NV_ORDERLY : 1; + unsigned int TPMA_NV_CLEAR_STCLEAR : 1; + unsigned int TPMA_NV_READLOCKED : 1; + unsigned int TPMA_NV_WRITTEN : 1; + unsigned int TPMA_NV_PLATFORMCREATE : 1; + unsigned int TPMA_NV_READ_STCLEAR : 1; +} TPMA_NV ; + +// Table 196 -- TPMS_NV_PUBLIC Structure +typedef struct { + u32 index; + u16 name_alg; + TPMA_NV attr; + TPM2B_DIGEST auth_policy; + u16 data_size; +} TPMS_NV_PUBLIC; + +// Table 197 -- TPM2B_NV_PUBLIC Structure +typedef struct { + u16 size; + TPMS_NV_PUBLIC nv_public; +} NV_PUBLIC_2B; + +typedef union { + NV_PUBLIC_2B t; + TPM2B b; +} TPM2B_NV_PUBLIC; + +// Table 203 -- TPMS_CREATION_DATA Structure +typedef struct { + TPML_PCR_SELECTION pcr_select; + TPM2B_DIGEST pcr_digest; + TPMA_LOCALITY locality; + u16 parent_name_alg; + TPM2B_NAME parent_name; + TPM2B_NAME parent_qualified_name; + TPM2B_DATA outside_info; +} TPMS_CREATION_DATA; + +// Table 204 -- TPM2B_CREATION_DATA Structure +typedef struct { + u16 size; + TPMS_CREATION_DATA data; +} CREATION_DATA_2B; + +typedef union { + CREATION_DATA_2B t; + TPM2B b; +} TPM2B_CREATION_DATA; + + +#define MAX_SESSIONS 3 + +// Input structure for session data for a single session, +typedef struct { + u32 session_handle; + TPM2B_NONCE nonce; + TPMA_SESSION session_attr; + TPM2B_AUTH hmac; +} TPM_CMD_SESSION_DATA_IN ; + +// Input structure for sessions data. +typedef struct { + u8 num_sessions; + TPM_CMD_SESSION_DATA_IN sessions[MAX_SESSION_NUM]; +} TPM_CMD_SESSIONS_IN; + +// Output structure for session data for a single session. +typedef struct { + TPM2B_NONCE nonce; + TPMA_SESSION session_attr; + TPM2B_AUTH hmac; +} TPM_CMD_SESSION_DATA_OUT; + +// Output structure for sessions data. +typedef struct { + u8 num_sessions; + TPM_CMD_SESSION_DATA_OUT sessions[MAX_SESSION_NUM]; +} TPM_CMD_SESSIONS_OUT; + + +/* + * command parameter related structure + */ + +typedef struct { + TPML_PCR_SELECTION pcr_selection; +} tpm_pcr_read_in; + +typedef struct { + u32 pcr_update_counter; + TPML_PCR_SELECTION pcr_selection; + TPML_DIGEST pcr_values; +} tpm_pcr_read_out; + +typedef struct { + u32 pcr_handle; + TPM_CMD_SESSIONS_IN sessions; + TPML_DIGEST_VALUES digests; +} tpm_pcr_extend_in; + +typedef struct { + TPM_CMD_SESSIONS_OUT sessions; +} tpm_pcr_extend_out; + +typedef struct { + u32 pcr_handle; + TPM_CMD_SESSIONS_IN sessions; + TPM2B_EVENT data; +} tpm_pcr_event_in; + +typedef struct { + TPML_DIGEST_VALUES digests; + TPM_CMD_SESSIONS_OUT sessions; +} tpm_pcr_event_out; + +typedef struct { + u32 pcr_handle; + TPM_CMD_SESSIONS_IN sessions; +} tpm_pcr_reset_in; + +typedef struct { + TPM_CMD_SESSIONS_OUT sessions; +} tpm_pcr_reset_out; + +typedef struct { + TPM2B_AUTH auth; + u16 hash_alg; +} tpm_sequence_start_in; + +typedef struct { + u32 handle; +} tpm_sequence_start_out; + +typedef struct { + u32 handle; + TPM_CMD_SESSIONS_IN sessions; + TPM2B_MAX_BUFFER buf; +} tpm_sequence_update_in; + +typedef struct { + TPM_CMD_SESSIONS_OUT sessions; +} tpm_sequence_update_out; + +typedef struct { + u32 pcr_handle; + u32 seq_handle; + TPM_CMD_SESSIONS_IN sessions; + TPM2B_MAX_BUFFER buf; +} tpm_sequence_complete_in; + +typedef struct { + TPML_DIGEST_VALUES results; + TPM_CMD_SESSIONS_OUT sessions; +} tpm_sequence_complete_out; + +typedef struct { + u32 seq_handle; + TPM_CMD_SESSIONS_IN sessions; + TPM2B_MAX_BUFFER buf; + u32 hierarchy; +} tpm_sequence_complete2_in; + +typedef struct { + TPML_DIGEST_VALUES results; + TPMT_TK_HASHCHECK validation; + TPM_CMD_SESSIONS_OUT sessions; +} tpm_sequence_complete2_out; + +typedef struct { + u32 handle; + u32 index; + TPM_CMD_SESSIONS_IN sessions; + u16 size; + u16 offset; +} tpm_nv_read_in; + +typedef struct { + TPM2B_MAX_NV_BUFFER data; + TPM_CMD_SESSIONS_OUT sessions; +} tpm_nv_read_out; + +typedef struct { + u32 handle; + u32 index; + TPM_CMD_SESSIONS_IN sessions; + TPM2B_MAX_NV_BUFFER data; + u16 offset; +} tpm_nv_write_in; + +typedef struct { + TPM_CMD_SESSIONS_OUT sessions; +} tpm_nv_write_out; + +typedef struct { + u32 handle; + TPM_CMD_SESSIONS_IN sessions; + TPM2B_AUTH auth; + TPM2B_NV_PUBLIC public_info; +} tpm_nv_define_space_in; + +typedef struct { + TPM_CMD_SESSIONS_OUT sessions; +} tpm_nv_define_space_out; + +typedef struct { + u32 handle; + u32 index; + TPM_CMD_SESSIONS_IN sessions; +} tpm_nv_undefine_space_in; + +typedef struct { + TPM_CMD_SESSIONS_OUT sessions; +} tpm_nv_undefine_space_out; + +typedef struct { + u32 index; +} tpm_nv_read_public_in; + +typedef struct { + TPM2B_NV_PUBLIC nv_public; + TPM2B_NAME nv_name; +} tpm_nv_read_public_out; + +typedef struct { + u16 bytes_req; +} tpm_get_random_in; + +typedef struct { + TPM2B_DIGEST random_bytes; +} tpm_get_random_out; + +typedef struct { + u32 capability; + u32 property; + u32 property_count; +} tpm_get_capability_in; + +typedef struct { + u8 more_data; + TPMS_CAPABILITY_DATA data; +} tpm_get_capability_out; + +typedef struct { + u32 primary_handle; + TPM_CMD_SESSIONS_IN sessions; + TPM2B_SENSITIVE_CREATE sensitive; + TPM2B_PUBLIC public; + TPM2B_DATA outside_info; + TPML_PCR_SELECTION creation_pcr; +} tpm_create_primary_in; + +typedef struct { + u32 obj_handle; + TPM2B_PUBLIC public; + TPM2B_CREATION_DATA creation_data; + TPM2B_DIGEST creation_hash; + TPMT_TK_CREATION creation_ticket; + TPM2B_NAME name; + TPM_CMD_SESSIONS_OUT sessions; +} tpm_create_primary_out; + +typedef struct { + u32 parent_handle; + TPM_CMD_SESSIONS_IN sessions; + TPM2B_SENSITIVE_CREATE sensitive; + TPM2B_PUBLIC public; + TPM2B_DATA outside_info; + TPML_PCR_SELECTION creation_pcr; +} tpm_create_in; + +typedef struct { + TPM2B_PRIVATE private; + TPM2B_PUBLIC public; + TPM2B_CREATION_DATA creation_data; + TPM2B_DIGEST creation_hash; + TPMT_TK_CREATION creation_ticket; + TPM_CMD_SESSIONS_OUT sessions; +} tpm_create_out; + +typedef struct { + u32 parent_handle; + TPM_CMD_SESSIONS_IN sessions; + TPM2B_PRIVATE private; + TPM2B_PUBLIC public; +} tpm_load_in; + +typedef struct { + u32 obj_handle; + TPM2B_NAME name; + TPM_CMD_SESSIONS_OUT sessions; +} tpm_load_out; + +typedef struct { + u32 item_handle; + TPM_CMD_SESSIONS_IN sessions; +} tpm_unseal_in; + +typedef struct { + TPM2B_SENSITIVE_DATA data; + TPM_CMD_SESSIONS_OUT sessions; +} tpm_unseal_out; + + +#endif /* __TPM20_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/txt/acmod.h b/tboot/include/txt/acmod.h new file mode 100644 index 0000000..33f8b28 --- /dev/null +++ b/tboot/include/txt/acmod.h @@ -0,0 +1,195 @@ +/* + * acmod.c: support functions for use of Intel(r) TXT Authenticated + * Code (AC) Modules + * + * Copyright (c) 2003-2011, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TXT_ACMOD_H__ +#define __TXT_ACMOD_H__ + +/* + * authenticated code (AC) module header (ver 0.0) + */ + +typedef union { + uint16_t _raw; + struct { + uint16_t reserved : 14; + uint16_t pre_production : 1; + uint16_t debug_signed : 1; + }; +} acm_flags_t; + +typedef struct { + uint16_t module_type; + uint16_t module_subtype; + uint32_t header_len; + uint32_t header_ver; /* currently 0.0 */ + uint16_t chipset_id; + acm_flags_t flags; + uint32_t module_vendor; + uint32_t date; + uint32_t size; + uint16_t txt_svn; + uint16_t se_svn; + uint32_t code_control; + uint32_t error_entry_point; + uint32_t gdt_limit; + uint32_t gdt_base; + uint32_t seg_sel; + uint32_t entry_point; + uint8_t reserved2[64]; + uint32_t key_size; + uint32_t scratch_size; + uint8_t rsa2048_pubkey[256]; + uint32_t pub_exp; + uint8_t rsa2048_sig[256]; + uint32_t scratch[143];// + uint8_t user_area[]; +} acm_hdr_t; + +/* value of module_type field */ +#define ACM_TYPE_CHIPSET 0x02 + +/* value of module_subtype field */ +#define ACM_SUBTYPE_RESET 0x01 + +/* value of module_vendor field */ +#define ACM_VENDOR_INTEL 0x8086 + +typedef union { + uint32_t _raw; + struct { + uint32_t ext_policy : 2; + uint32_t tpm_family : 4; + uint32_t tpm_nv_index_set : 1; + uint32_t reserved : 25; + }; +} tpm_cap_t; + +/* ext_policy field values */ +#define TPM_EXT_POLICY_ILLEGAL 0x00 +#define TPM_EXT_POLICY_ALG_AGILE_CMD 0x01 +#define TPM_EXT_POLICY_EMBEDED_ALGS 0x10 +#define TPM_EXT_POLICY_BOTH 0x11 + +/* tpm_family field values */ +#define TPM_FAMILY_ILLEGAL 0x0000 +#define TPM_FAMILY_DTPM_12 0x0001 +#define TPM_FAMILY_DTPM_20 0x0010 +#define TPM_FAMILY_DTPM_BOTH 0x0011 +#define TPM_FAMILY_PTT_20 0x1000 + +typedef struct { + tpm_cap_t capabilities; + uint16_t count; + uint16_t alg_id[]; +} tpm_info_list_t; + +typedef struct __packed { + uuid_t uuid; + uint8_t chipset_acm_type; + uint8_t version; /* currently 4 */ + uint16_t length; + uint32_t chipset_id_list; + uint32_t os_sinit_data_ver; + uint32_t min_mle_hdr_ver; + txt_caps_t capabilities; + uint8_t acm_ver; + uint8_t reserved[3]; + /* versions >= 4 */ + uint32_t processor_id_list; + /* versions >= 5 */ + uint32_t tpm_info_list_off; +} acm_info_table_t; + +/* ACM UUID value */ +#define ACM_UUID_V3 {0x7fc03aaa, 0x46a7, 0x18db, 0xac2e, \ + {0x69, 0x8f, 0x8d, 0x41, 0x7f, 0x5a}} + +/* chipset_acm_type field values */ +#define ACM_CHIPSET_TYPE_BIOS 0x00 +#define ACM_CHIPSET_TYPE_SINIT 0x01 +#define ACM_CHIPSET_TYPE_BIOS_REVOC 0x08 +#define ACM_CHIPSET_TYPE_SINIT_REVOC 0x09 + +typedef struct __packed { + uint32_t flags; + uint16_t vendor_id; + uint16_t device_id; + uint16_t revision_id; + uint16_t reserved; + uint32_t extended_id; +} acm_chipset_id_t; + +typedef struct __packed { + uint32_t count; + acm_chipset_id_t chipset_ids[]; +} acm_chipset_id_list_t; + +typedef struct __packed { + uint32_t fms; + uint32_t fms_mask; + uint64_t platform_id; + uint64_t platform_mask; +} acm_processor_id_t; + +typedef struct __packed { + uint32_t count; + acm_processor_id_t processor_ids[]; +} acm_processor_id_list_t; + +acm_hdr_t *g_sinit; + +void print_txt_caps(const char *prefix, txt_caps_t caps); +bool is_racm_acmod(const void *acmod_base, uint32_t acmod_size, bool quiet); +acm_hdr_t *copy_racm(const acm_hdr_t *racm); +bool verify_racm(const acm_hdr_t *acm_hdr); +bool is_sinit_acmod(const void *acmod_base, uint32_t acmod_size, bool quiet); +bool does_acmod_match_platform(const acm_hdr_t* hdr); +acm_hdr_t *copy_sinit(const acm_hdr_t *sinit); +bool verify_acmod(const acm_hdr_t *acm_hdr); +uint32_t get_supported_os_sinit_data_ver(const acm_hdr_t* hdr); +txt_caps_t get_sinit_capabilities(const acm_hdr_t* hdr); +tpm_info_list_t *get_tpm_info_list(const acm_hdr_t* hdr); +void verify_IA32_se_svn_status(const acm_hdr_t *acm_hdr); +#endif /* __TXT_ACMOD_H__ */ + +/* + * Local variables: + * mode: C + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/txt/config_regs.h b/tboot/include/txt/config_regs.h new file mode 100644 index 0000000..4d02ea4 --- /dev/null +++ b/tboot/include/txt/config_regs.h @@ -0,0 +1,240 @@ +/* + * config_regs.h: Intel(r) TXT configuration register -related definitions + * + * Copyright (c) 2003-2011, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TXT_CONFIG_REGS_H__ +#define __TXT_CONFIG_REGS_H__ + +/* + * TXT configuration registers (offsets from TXT_{PUB, PRIV}_CONFIG_REGS_BASE) + */ + +#define TXT_PUB_CONFIG_REGS_BASE 0xfed30000 +#define TXT_PRIV_CONFIG_REGS_BASE 0xfed20000 + +#define TXT_CONFIG_REGS_SIZE (TXT_PUB_CONFIG_REGS_BASE - \ + TXT_PRIV_CONFIG_REGS_BASE) + +/* offsets to config regs (from either public or private _BASE) */ +#define TXTCR_STS 0x0000 +#define TXTCR_ESTS 0x0008 +#define TXTCR_ERRORCODE 0x0030 +#define TXTCR_CMD_RESET 0x0038 +#define TXTCR_CMD_CLOSE_PRIVATE 0x0048 +#define TXTCR_VER_FSBIF 0x0100 +#define TXTCR_DIDVID 0x0110 +#define TXTCR_VER_QPIIF 0x0200 +#define TXTCR_CMD_UNLOCK_MEM_CONFIG 0x0218 +#define TXTCR_SINIT_BASE 0x0270 +#define TXTCR_SINIT_SIZE 0x0278 +#define TXTCR_MLE_JOIN 0x0290 +#define TXTCR_HEAP_BASE 0x0300 +#define TXTCR_HEAP_SIZE 0x0308 +#define TXTCR_MSEG_BASE 0x0310 +#define TXTCR_MSEG_SIZE 0x0318 +#define TXTCR_DPR 0x0330 +#define TXTCR_CMD_OPEN_LOCALITY1 0x0380 +#define TXTCR_CMD_CLOSE_LOCALITY1 0x0388 +#define TXTCR_CMD_OPEN_LOCALITY2 0x0390 +#define TXTCR_CMD_CLOSE_LOCALITY2 0x0398 +#define TXTCR_PUBLIC_KEY 0x0400 +#define TXTCR_CMD_SECRETS 0x08e0 +#define TXTCR_CMD_NO_SECRETS 0x08e8 +#define TXTCR_E2STS 0x08f0 + +/* + * format of ERRORCODE register + */ +typedef union { + uint64_t _raw; + struct { + uint64_t type : 30; /* external-specific error code */ + uint64_t external : 1; /* 0=from proc, 1=from external SW */ + uint64_t valid : 1; /* 1=valid */ + }; +} txt_errorcode_t; + +/* + * format of ESTS register + */ +typedef union { + uint64_t _raw; + struct { + uint64_t txt_reset_sts : 1; + }; +} txt_ests_t; + +/* + * format of E2STS register + */ +typedef union { + uint64_t _raw; + struct { + uint64_t reserved : 1; + uint64_t secrets_sts : 1; + }; +} txt_e2sts_t; + +/* + * format of STS register + */ +typedef union { + uint64_t _raw; + struct { + uint64_t senter_done_sts : 1; + uint64_t sexit_done_sts : 1; + uint64_t reserved1 : 4; + uint64_t mem_config_lock_sts : 1; + uint64_t private_open_sts : 1; + uint64_t reserved2 : 7; + uint64_t locality_1_open_sts : 1; + uint64_t locality_2_open_sts : 1; + }; +} txt_sts_t; + +/* + * format of DIDVID register + */ +typedef union { + uint64_t _raw; + struct { + uint16_t vendor_id; + uint16_t device_id; + uint16_t revision_id; + uint16_t reserved; + }; +} txt_didvid_t; + +/* + * format of VER.FSBIF and VER.QPIIF registers + */ +typedef union { + uint64_t _raw; + struct { + uint64_t reserved : 31; + uint64_t prod_fused : 1; + }; +} txt_ver_fsbif_qpiif_t; + +/* + * format of DPR register + */ +typedef union { + uint64_t _raw; + struct { + uint64_t lock : 1; + uint64_t reserved1 : 3; + uint64_t size : 8; + uint64_t reserved2 : 8; + uint64_t top : 12; + uint64_t reserved3 : 32; + }; +} txt_dpr_t; + +/* + * RLP JOIN structure for GETSEC[WAKEUP] and MLE_JOIN register + */ +typedef struct { + uint32_t gdt_limit; + uint32_t gdt_base; + uint32_t seg_sel; /* cs (ds, es, ss are seg_sel+8) */ + uint32_t entry_point; /* phys addr */ +} mle_join_t; + +/* + * format of MSEG header + */ +typedef struct { + uint32_t revision_id; + uint32_t smm_mon_feat; + uint32_t gdtr_limit; + uint32_t gdtr_base_offset; + uint32_t cs_sel; + uint32_t eip_offset; + uint32_t esp_offset; + uint32_t cr3_offset; +} mseg_hdr_t; + +/* TODO these are causing warnings - changed to ull */ + +/* + * fns to read/write TXT config regs + */ + +#ifndef IS_INCLUDED +static inline uint64_t read_config_reg(uint64_t config_regs_base, uint32_t reg) +{ + /* these are MMIO so make sure compiler doesn't optimize */ + return *(volatile uint64_t *)(unsigned long long)(config_regs_base + reg); +} +#endif + +static inline void write_config_reg(uint64_t config_regs_base, uint32_t reg, + uint64_t val) +{ + /* these are MMIO so make sure compiler doesn't optimize */ + *(volatile uint64_t *)(unsigned long long)(config_regs_base + reg) = val; +} + +static inline uint64_t read_pub_config_reg(uint32_t reg) +{ + return read_config_reg(TXT_PUB_CONFIG_REGS_BASE, reg); +} + +static inline void write_pub_config_reg(uint32_t reg, uint64_t val) +{ + write_config_reg(TXT_PUB_CONFIG_REGS_BASE, reg, val); +} + +static inline uint64_t read_priv_config_reg(uint32_t reg) +{ + return read_config_reg(TXT_PRIV_CONFIG_REGS_BASE, reg); +} + +static inline void write_priv_config_reg(uint32_t reg, uint64_t val) +{ + write_config_reg(TXT_PRIV_CONFIG_REGS_BASE, reg, val); +} + +#endif /* __TXT_CONFIG_REGS_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/txt/errorcode.h b/tboot/include/txt/errorcode.h new file mode 100644 index 0000000..fe85a3c --- /dev/null +++ b/tboot/include/txt/errorcode.h @@ -0,0 +1,105 @@ +/* + * errorcode.h: Intel(r) TXT error definitions for ERRORCODE config register + * + * Copyright (c) 2003-2011, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TXT_ERRORCODE_H__ +#define __TXT_ERRORCODE_H__ + +/* + * error values for processor error codes (ERRORCODE.external = 0) + */ +#define TXT_ERR_PROC_LEGACY_SHUTDOWN 0 +#define TXT_ERR_PROC_INVALID_ACM_MEM_TYPE 5 +#define TXT_ERR_PROC_UNSUPPORTED_ACM 6 +#define TXT_ERR_PROC_AUTH_FAIL 7 +#define TXT_ERR_PROC_INVALID_ACM_FORMAT 8 +#define TXT_ERR_PROC_UNEXPECTED_HITM 9 +#define TXT_ERR_PROC_INVALID_EVENT 10 +#define TXT_ERR_PROC_INVALID_JOIN_FORMAT 11 +#define TXT_ERR_PROC_UNRECOVERABLE_MCE 12 +#define TXT_ERR_PROC_VMX_ABORT 13 +#define TXT_ERR_PROC_ACM_CORRUPT 14 +#define TXT_ERR_PROC_INVALID_VIDB_RATIO 15 + +/* + * for SW errors (ERRORCODE.external = 1) + */ +typedef union { + uint32_t _raw; + struct { + uint32_t err1 : 15; /* specific to src */ + uint32_t src : 1; /* 0=ACM, 1=other */ + uint32_t err2 : 14; /* specific to src */ + uint32_t external : 1; /* always 1 for this type */ + uint32_t valid : 1; /* always 1 */ + }; +} txt_errorcode_sw_t; + +/* + * ACM errors (txt_errorcode_sw_t.src=0), format of err1+src+err2 fields + */ +typedef union __attribute__((packed)){ + uint32_t _raw; + struct __attribute__((packed)){ + uint32_t acm_type : 4; /* 0000=BIOS ACM, 0001=SINIT, */ + /* 0010-1111=reserved */ + uint32_t progress : 6; + uint32_t error : 5; + uint32_t src : 1; /* above value */ + union __attribute__((packed)){ + struct __attribute__((packed)) { /* progress=0x0d, error=1010 */ + uint32_t tpm_err : 9; + uint32_t reserved1 : 5; + }; + struct __attribute__((packed)) { /* progress=0x10 */ + uint32_t lcp_minor : 6; + uint32_t lcp_index : 3; + uint32_t reserved2 : 5; + }; + }; /* sub-error */ + }; +} acmod_error_t; + +#endif /* __TXT_ERRORCODE_H__ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/txt/heap.h b/tboot/include/txt/heap.h new file mode 100644 index 0000000..c4e2d51 --- /dev/null +++ b/tboot/include/txt/heap.h @@ -0,0 +1,377 @@ +/* + * heap.h: Intel(r) TXT heap definitions + * + * Copyright (c) 2003-2011, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TXT_HEAP_H__ +#define __TXT_HEAP_H__ + +/* + * Extensible TXT heap data structure + */ + +typedef struct __packed { + uint32_t type; + uint32_t size; + uint8_t data[]; +} heap_ext_data_element_t; + +/* + * HEAP_END_ELEMENT + */ +#define HEAP_EXTDATA_TYPE_END 0 + +/* size == 8; there is no data[] */ + +/* + * HEAP_BIOS_SPEC_VER_ELEMENT + */ +#define HEAP_EXTDATA_TYPE_BIOS_SPEC_VER 1 + +typedef struct __packed { + uint16_t spec_ver_major; + uint16_t spec_ver_minor; + uint16_t spec_ver_rev; +} heap_bios_spec_ver_elt_t; + +/* + * HEAP_ACM_ELEMENT + */ +#define HEAP_EXTDATA_TYPE_ACM 2 + +typedef struct __packed { + uint32_t num_acms; + uint64_t acm_addrs[]; +} heap_acm_elt_t; + +/* + * HEAP_CUSTOM_ELEMENT + */ +#define HEAP_EXTDATA_TYPE_CUSTOM 4 + +typedef struct __packed { + uuid_t uuid; + uint8_t data[]; +} heap_custom_elt_t; + +/* + * HEAP_EVENT_LOG_POINTER_ELEMENT + */ +#define HEAP_EXTDATA_TYPE_TPM_EVENT_LOG_PTR 5 + +typedef struct __packed { + uint64_t event_log_phys_addr; +} heap_event_log_ptr_elt_t; + +typedef struct __packed { + uint32_t pcr_index; + uint32_t type; + sha1_hash_t digest; + uint32_t data_size; + uint8_t data[]; +} tpm12_pcr_event_t; + +#define EVTLOG_SIGNATURE "TXT Event Container\0" +#define EVTLOG_CNTNR_MAJOR_VER 1 +#define EVTLOG_CNTNR_MINOR_VER 0 +#define EVTLOG_EVT_MAJOR_VER 1 +#define EVTLOG_EVT_MINOR_VER 0 +typedef struct __packed { + uint8_t signature[20]; + uint8_t reserved[12]; + uint8_t container_ver_major; + uint8_t container_ver_minor; + uint8_t pcr_event_ver_major; + uint8_t pcr_event_ver_minor; + uint32_t size; + uint32_t pcr_events_offset; + uint32_t next_event_offset; + tpm12_pcr_event_t pcr_events[]; +} event_log_container_t; + +/* + * HEAP_EVENT_LOG_POINTER_ELEMENT2 + */ +#define HEAP_EXTDATA_TYPE_TPM_EVENT_LOG_PTR_2 7 + +#define DIGEST_ALG_ID_SHA_1 0x00000001 +#define DIGEST_ALG_ID_SHA_256 0x00000002 +#define DIGEST_ALG_ID_SHA_384 0x00000003 +#define DIGEST_ALG_ID_SHA_512 0x00000004 +#define DIGEST_ALG_ID_SM3 0x00000005 +static inline unsigned int get_evtlog_digest_id(uint16_t hash_alg) +{ + if ( hash_alg == TB_HALG_SHA1 ) + return DIGEST_ALG_ID_SHA_1; + else if ( hash_alg == TB_HALG_SHA256 ) + return DIGEST_ALG_ID_SHA_256; + else if ( hash_alg == TB_HALG_SM3 ) + return DIGEST_ALG_ID_SM3; + else if ( hash_alg == TB_HALG_SHA384 ) + return DIGEST_ALG_ID_SHA_384; + else if ( hash_alg == TB_HALG_SHA512 ) + return DIGEST_ALG_ID_SHA_512; + else + return 0; +} + +typedef struct __packed { + uint8_t signature[16]; + uint32_t revision; + uint32_t digest_id; + uint32_t digest_size; +} tpm20_log_descr_t; + +typedef struct __packed { + uint16_t alg; + uint16_t reserved; + uint64_t phys_addr; + uint32_t size; + uint32_t pcr_events_offset; + uint32_t next_event_offset; +} heap_event_log_descr_t; + +typedef struct __packed { + uint32_t count; + heap_event_log_descr_t event_log_descr[]; +} heap_event_log_ptr_elt2_t; + + +/* + * data-passing structures contained in TXT heap: + * - BIOS + * - OS/loader to MLE + * - OS/loader to SINIT + * - SINIT to MLE + */ + +/* + * BIOS structure + */ +typedef struct __packed { + uint32_t version; /* currently 2-4 */ + uint32_t bios_sinit_size; + uint64_t lcp_pd_base; + uint64_t lcp_pd_size; + uint32_t num_logical_procs; + /* versions >= 3 */ + uint64_t flags; /* For TPM2, it is divided into sinit_flag and mle_flag */ + /* versions >= 4 */ + heap_ext_data_element_t ext_data_elts[]; +} bios_data_t; + +/* + * OS/loader to MLE structure + * - private to tboot (so can be any format we need) + */ +#define MAX_LCP_PO_DATA_SIZE 64*1024 /* 64k */ +#define MAX_EVENT_LOG_SIZE 5*4*1024 /* 4k*5 */ + +typedef struct __packed { + uint32_t version; /* currently 3 */ + mtrr_state_t saved_mtrr_state; /* saved prior to changes for SINIT */ + uint64_t saved_misc_enable_msr; /* saved prior to SENTER */ + /* PO policy data */ + uint8_t lcp_po_data[MAX_LCP_PO_DATA_SIZE]; + /* buffer for tpm event log */ + uint8_t event_log_buffer[MAX_EVENT_LOG_SIZE]; +} os_mle_data_t; + +#define MIN_OS_SINIT_DATA_VER 4 +#define MAX_OS_SINIT_DATA_VER 7 +#define OS_SINIT_FLAGS_EXTPOL_MASK 0x00000001 +/* + * OS/loader to SINIT structure + */ +typedef struct __packed { + uint32_t version; /* currently 4-7 */ + uint32_t flags; /* For TPM2: BIT0:= PCR Extend Policy Control */ + uint64_t mle_ptab; + uint64_t mle_size; + uint64_t mle_hdr_base; + uint64_t vtd_pmr_lo_base; + uint64_t vtd_pmr_lo_size; + uint64_t vtd_pmr_hi_base; + uint64_t vtd_pmr_hi_size; + uint64_t lcp_po_base; + uint64_t lcp_po_size; + txt_caps_t capabilities; + /* versions >= 5 */ + uint64_t efi_rsdt_ptr; + /* versions >= 6 */ + heap_ext_data_element_t ext_data_elts[]; +} os_sinit_data_t; + +/* + * SINIT to MLE structure + */ +#define MDR_MEMTYPE_GOOD 0x00 +#define MDR_MEMTYPE_SMM_OVERLAY 0x01 +#define MDR_MEMTYPE_SMM_NONOVERLAY 0x02 +#define MDR_MEMTYPE_PCIE_CONFIG_SPACE 0x03 +#define MDR_MEMTYPE_PROTECTED 0x04 + +typedef struct __packed { + uint64_t base; + uint64_t length; + uint8_t mem_type; + uint8_t reserved[7]; +} sinit_mdr_t; + +typedef struct __packed { + uint32_t version; /* currently 6-9 */ + sha1_hash_t bios_acm_id; /* only for tpm1.2 */ + uint32_t edx_senter_flags; /* only for tpm1.2 */ + uint64_t mseg_valid; /* only for tpm1.2 */ + sha1_hash_t sinit_hash; /* only for tpm1.2 */ + sha1_hash_t mle_hash; /* only for tpm1.2 */ + sha1_hash_t stm_hash; /* only for tpm1.2 */ + sha1_hash_t lcp_policy_hash; /* only for tpm1.2 */ + uint32_t lcp_policy_control; /* only for tpm1.2 */ + uint32_t rlp_wakeup_addr; + uint32_t reserved; + uint32_t num_mdrs; + uint32_t mdrs_off; + uint32_t num_vtd_dmars; + uint32_t vtd_dmars_off; + /* versions >= 8 */ + uint32_t proc_scrtm_status; /* only for tpm1.2 */ + /* versions >= 9 */ + heap_ext_data_element_t ext_data_elts[]; +} sinit_mle_data_t; + + +/* + * TXT heap data format and field accessor fns + */ + +/* + * offset length field + * ------ ------ ----- + * 0 8 bios_data_size + * 8 bios_data_size - 8 bios_data + * + * bios_data_size 8 os_mle_data_size + * bios_data_size + os_mle_data_size - 8 os_mle_data + * 8 + * + * bios_data_size + 8 os_sinit_data_size + * os_mle_data_size + * bios_data_size + os_sinit_data_size - 8 os_sinit_data + * os_mle_data_size + + * 8 + * + * bios_data_size + 8 sinit_mle_data_size + * os_mle_data_size + + * os_sinit_data_size + * bios_data_size + sinit_mle_data_size - 8 sinit_mle_data + * os_mle_data_size + + * os_sinit_data_size + + * 8 + */ + +typedef void txt_heap_t; + +/* TODO these are causing warnings - changed to ull */ + +/* this is a common use with annoying casting, so make it an inline */ +static inline txt_heap_t *get_txt_heap(void) +{ + return (txt_heap_t *)(unsigned long long)read_pub_config_reg(TXTCR_HEAP_BASE); +} + +static inline uint64_t get_bios_data_size(const txt_heap_t *heap) +{ + return *(uint64_t *)heap; +} + +static inline bios_data_t *get_bios_data_start(const txt_heap_t *heap) +{ + return (bios_data_t *)((char*)heap + sizeof(uint64_t)); +} + +static inline uint64_t get_os_mle_data_size(const txt_heap_t *heap) +{ + return *(uint64_t *)(heap + get_bios_data_size(heap)); +} + +static inline os_mle_data_t *get_os_mle_data_start(const txt_heap_t *heap) +{ + return (os_mle_data_t *)(heap + get_bios_data_size(heap) + + sizeof(uint64_t)); +} + +static inline uint64_t get_os_sinit_data_size(const txt_heap_t *heap) +{ + return *(uint64_t *)(heap + get_bios_data_size(heap) + + get_os_mle_data_size(heap)); +} + +static inline os_sinit_data_t *get_os_sinit_data_start(const txt_heap_t *heap) +{ + return (os_sinit_data_t *)(heap + get_bios_data_size(heap) + + get_os_mle_data_size(heap) + + sizeof(uint64_t)); +} + +static inline uint64_t get_sinit_mle_data_size(const txt_heap_t *heap) +{ + return *(uint64_t *)(heap + get_bios_data_size(heap) + + get_os_mle_data_size(heap) + + get_os_sinit_data_size(heap)); +} + +static inline sinit_mle_data_t *get_sinit_mle_data_start(const txt_heap_t *heap) +{ + return (sinit_mle_data_t *)(heap + get_bios_data_size(heap) + + get_os_mle_data_size(heap) + + get_os_sinit_data_size(heap) + + sizeof(uint64_t)); +} + +uint64_t calc_os_sinit_data_size(uint32_t version); +bool verify_txt_heap(const txt_heap_t *txt_heap, bool bios_data_only); +bool verify_bios_data(const txt_heap_t *txt_heap); +void print_os_sinit_data(const os_sinit_data_t *os_sinit_data); + +#endif /* __TXT_HEAP_H__ */ + + +/* + * Local variables: + * mode: C + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/txt/mtrrs.h b/tboot/include/txt/mtrrs.h new file mode 100644 index 0000000..8b61f6e --- /dev/null +++ b/tboot/include/txt/mtrrs.h @@ -0,0 +1,149 @@ +/* + * mtrrs.c: Intel(r) TXT MTRR-related definitions + * + * Copyright (c) 2003-2010, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TXT_MTRRS_H__ +#define __TXT_MTRRS_H__ + +#include + +enum fix_mtrr_t { + MTRR_FIX64K_00000 = 0x250, + MTRR_FIX16K_80000 = 0x258, + MTRR_FIX16K_A0000 = 0x259, + MTRR_FIX4K_C0000 = 0x268, + MTRR_FIX4K_C8000 = 0x269, + MTRR_FIX4K_D0000 = 0x26A, + MTRR_FIX4K_D8000 = 0x26B, + MTRR_FIX4K_E0000 = 0x26C, + MTRR_FIX4K_E8000 = 0x26D, + MTRR_FIX4K_F0000 = 0x26E, + MTRR_FIX4K_F8000 = 0x26F +}; + +typedef union { + uint64_t raw; + uint8_t type[8]; +} mtrr_fix_types_t; + +enum var_mtrr_t { + MTRR_PHYS_BASE0_MSR = 0x200, + MTRR_PHYS_MASK0_MSR = 0x201, + MTRR_PHYS_BASE1_MSR = 0x202, + MTRR_PHYS_MASK1_MSR = 0x203, + MTRR_PHYS_BASE2_MSR = 0x204, + MTRR_PHYS_MASK2_MSR = 0x205, + MTRR_PHYS_BASE3_MSR = 0x206, + MTRR_PHYS_MASK3_MSR = 0x207, + MTRR_PHYS_BASE4_MSR = 0x208, + MTRR_PHYS_MASK4_MSR = 0x209, + MTRR_PHYS_BASE5_MSR = 0x20A, + MTRR_PHYS_MASK5_MSR = 0x20B, + MTRR_PHYS_BASE6_MSR = 0x20C, + MTRR_PHYS_MASK6_MSR = 0x20D, + MTRR_PHYS_BASE7_MSR = 0x20E, + MTRR_PHYS_MASK7_MSR = 0x20F +}; + +typedef union { + uint64_t raw; + struct { + uint64_t vcnt : 8; /* num variable MTRR pairs */ + uint64_t fix : 1; /* fixed range MTRRs are supported */ + uint64_t reserved1 : 1; + uint64_t wc : 1; /* write-combining mem type supported */ + uint64_t reserved2 : 53; + }; +} mtrr_cap_t; + +typedef union { + uint64_t raw; + struct { + uint64_t type : 8; + uint64_t reserved1 : 2; + uint64_t fe : 1; /* fixed MTRR enable */ + uint64_t e : 1; /* (all) MTRR enable */ + uint64_t reserved2 : 52; + }; +} mtrr_def_type_t; + +typedef union { + uint64_t raw; + struct { + uint64_t type : 8; + uint64_t reserved1 : 4; + uint64_t base : 52; /* define as max width and mask w/ */ + /* MAXPHYADDR when using */ + }; +} mtrr_physbase_t; + +typedef union { + uint64_t raw; + struct { + uint64_t reserved1 : 11; + uint64_t v : 1; /* valid */ + uint64_t mask : 52; /* define as max width and mask w/ */ + /* MAXPHYADDR when using */ + }; +} mtrr_physmask_t; + +/* current procs only have 8, so this should hold us for a while */ +#define MAX_VARIABLE_MTRRS 16 + +typedef struct { + mtrr_def_type_t mtrr_def_type; + unsigned int num_var_mtrrs; + mtrr_physbase_t mtrr_physbases[MAX_VARIABLE_MTRRS]; + mtrr_physmask_t mtrr_physmasks[MAX_VARIABLE_MTRRS]; +} mtrr_state_t; + +bool set_mtrrs_for_acmod(const acm_hdr_t *hdr); +void save_mtrrs(mtrr_state_t *saved_state); +void set_all_mtrrs(bool enable); +bool set_mem_type(const void *base, uint32_t size, uint32_t mem_type); +void restore_mtrrs(const mtrr_state_t *saved_state); +bool validate_mtrrs(const mtrr_state_t *saved_state); + +#endif /*__TXT_MTRRS_H__ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/txt/smx.h b/tboot/include/txt/smx.h new file mode 100644 index 0000000..93645c7 --- /dev/null +++ b/tboot/include/txt/smx.h @@ -0,0 +1,171 @@ +/* + * smx.h: Intel(r) TXT SMX architecture-related definitions + * + * Copyright (c) 2003-2008, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TXT_SMX_H__ +#define __TXT_SMX_H__ + +/* + * GETSEC[] instructions + */ + +/* GETSEC instruction opcode */ +#define IA32_GETSEC_OPCODE ".byte 0x0f,0x37" + +/* GETSEC leaf function codes */ +#define IA32_GETSEC_CAPABILITIES 0 +#define IA32_GETSEC_ENTERACCS 2 +#define IA32_GETSEC_SENTER 4 +#define IA32_GETSEC_SEXIT 5 +#define IA32_GETSEC_PARAMETERS 6 +#define IA32_GETSEC_SMCTRL 7 +#define IA32_GETSEC_WAKEUP 8 + +/* + * GETSEC[] leaf functions + */ + +typedef union { + uint32_t _raw; + struct { + uint32_t chipset_present : 1; + uint32_t undefined1 : 1; + uint32_t enteraccs : 1; + uint32_t exitac : 1; + uint32_t senter : 1; + uint32_t sexit : 1; + uint32_t parameters : 1; + uint32_t smctrl : 1; + uint32_t wakeup : 1; + uint32_t undefined9 : 22; + uint32_t extended_leafs : 1; + }; +} capabilities_t; + +static inline capabilities_t __getsec_capabilities(uint32_t index) +{ + uint32_t cap; + __asm__ __volatile__ (IA32_GETSEC_OPCODE "\n" + : "=a"(cap) + : "a"(IA32_GETSEC_CAPABILITIES), "b"(index)); + return (capabilities_t)cap; +} + +/* helper fn. for getsec_capabilities */ +/* this is arbitrary and can be increased when needed */ +#define MAX_SUPPORTED_ACM_VERSIONS 16 + +typedef struct { + struct { + uint32_t mask; + uint32_t version; + } acm_versions[MAX_SUPPORTED_ACM_VERSIONS]; + int n_versions; + uint32_t acm_max_size; + uint32_t acm_mem_types; + uint32_t senter_controls; + bool proc_based_scrtm; + bool preserve_mce; +} getsec_parameters_t; + +bool get_parameters(getsec_parameters_t *params); + + +static inline void __getsec_senter(uint32_t sinit_base, uint32_t sinit_size) +{ + __asm__ __volatile__ (IA32_GETSEC_OPCODE "\n" + : + : "a"(IA32_GETSEC_SENTER), + "b"(sinit_base), + "c"(sinit_size), + "d"(0x0)); +} + +static inline void __getsec_sexit(void) +{ + __asm__ __volatile__ (IA32_GETSEC_OPCODE "\n" + : : "a"(IA32_GETSEC_SEXIT)); +} + +static inline void __getsec_wakeup(void) +{ + __asm__ __volatile__ (IA32_GETSEC_OPCODE "\n" + : : "a"(IA32_GETSEC_WAKEUP)); +} + +static inline void __getsec_smctrl(void) +{ + __asm__ __volatile__ (IA32_GETSEC_OPCODE "\n" + : : "a"(IA32_GETSEC_SMCTRL), "b"(0x0)); +} + +static inline void __getsec_parameters(uint32_t index, int* param_type, + uint32_t* peax, uint32_t* pebx, + uint32_t* pecx) +{ + uint32_t eax=0, ebx=0, ecx=0; + __asm__ __volatile__ (IA32_GETSEC_OPCODE "\n" + : "=a"(eax), "=b"(ebx), "=c"(ecx) + : "a"(IA32_GETSEC_PARAMETERS), "b"(index)); + + if ( param_type != NULL ) *param_type = eax & 0x1f; + if ( peax != NULL ) *peax = eax; + if ( pebx != NULL ) *pebx = ebx; + if ( pecx != NULL ) *pecx = ecx; +} + +static inline void __getsec_enteraccs(uint32_t acm_base, uint32_t acm_size, + uint32_t fn) +{ + __asm__ __volatile__ (IA32_GETSEC_OPCODE "\n" + : + : "a"(IA32_GETSEC_ENTERACCS), + "b"(acm_base), + "c"(acm_size), + "D"(0), + "S"(fn)); +} + + +#endif /* __TXT_SMX_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/txt/txt.h b/tboot/include/txt/txt.h new file mode 100644 index 0000000..2555e70 --- /dev/null +++ b/tboot/include/txt/txt.h @@ -0,0 +1,76 @@ +/* + * txt.h: Intel(r) TXT support functions + * + * Copyright (c) 2003-2008, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TXT_TXT_H__ +#define __TXT_TXT_H__ + +// #include + +void txt_init_mle_header(void); +bool txt_build_mle_pagetable(void); +bool txt_is_launched(void); +bool txt_get_error(void); +void txt_get_racm_error(void); +tb_error_t supports_txt(void); +tb_error_t txt_verify_platform(void); +bool txt_prepare_cpu(void); +tb_error_t txt_launch_environment(void); +/* TODO need to address the loader business, stub out for now +tb_error_t txt_launch_racm(loader_ctx *lctx); +*/ +void txt_post_launch(void); +tb_error_t txt_protect_mem_regions(void); +tb_error_t txt_post_launch_verify_platform(void); +bool txt_s3_launch_environment(void); +void txt_shutdown(void); +bool txt_is_powercycle_required(void); +void ap_wait(unsigned int cpuid); + +uint32_t g_using_da; +atomic_t ap_wfs_count; + +#endif /* __TXT_TXT_H__ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ + diff --git a/tboot/include/txt/verify.h b/tboot/include/txt/verify.h new file mode 100644 index 0000000..659af15 --- /dev/null +++ b/tboot/include/txt/verify.h @@ -0,0 +1,57 @@ +/* + * verify.h: support functions for platform Intel(r) TXT verification + * + * Copyright (c) 2003-2008, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TXT_VERIFY_H__ +#define __TXT_VERIFY_H__ + +void set_vtd_pmrs(os_sinit_data_t *os_sinit_data, + uint64_t min_lo_ram, uint64_t max_lo_ram, + uint64_t min_hi_ram, uint64_t max_hi_ram); +bool verify_e820_map(sinit_mdr_t* mdrs_base, uint32_t num_mdrs); +bool verify_stm(unsigned int cpuid); +bool use_mwait(void); + +#endif /* __TXT_VERIFY_H__ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/txt/vmcs.h b/tboot/include/txt/vmcs.h new file mode 100644 index 0000000..74f6ecc --- /dev/null +++ b/tboot/include/txt/vmcs.h @@ -0,0 +1,346 @@ +/* + * vmcs.h: VMCS definitions for creation of APs mini-guests + * + * Copyright (c) 2003-2009, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TXT_VMCS_H__ +#define __TXT_VMCS_H__ + +struct vmcs_struct { + uint32_t vmcs_revision_id; + unsigned char data[0]; /* vmcs size is read from MSR */ +}; + +union vmcs_arbytes { + struct arbyte_fields { + unsigned int seg_type : 4, + s : 1, + dpl : 2, + p : 1, + reserved0 : 4, + avl : 1, + reserved1 : 1, + default_ops_size: 1, + g : 1, + null_bit : 1, + reserved2 : 15; + } fields; + unsigned int bytes; +}; + +#define CPU_BASED_HLT_EXITING 0x00000080 +#define CPU_BASED_INVDPG_EXITING 0x00000200 +#define CPU_BASED_MWAIT_EXITING 0x00000400 + +#define PIN_BASED_EXT_INTR_MASK 0x00000001 +#define PIN_BASED_NMI_EXITING 0x00000008 + +#define VM_EXIT_IA32E_MODE 0x00000200 +#define VM_EXIT_ACK_INTR_ON_EXIT 0x00008000 + +#define VM_ENTRY_IA32E_MODE 0x00000200 +#define VM_ENTRY_SMM 0x00000400 +#define VM_ENTRY_DEACT_DUAL_MONITOR 0x00000800 + + +/* VMCS Encordings */ +enum vmcs_field { + GUEST_ES_SELECTOR = 0x00000800, + GUEST_CS_SELECTOR = 0x00000802, + GUEST_SS_SELECTOR = 0x00000804, + GUEST_DS_SELECTOR = 0x00000806, + GUEST_FS_SELECTOR = 0x00000808, + GUEST_GS_SELECTOR = 0x0000080a, + GUEST_LDTR_SELECTOR = 0x0000080c, + GUEST_TR_SELECTOR = 0x0000080e, + HOST_ES_SELECTOR = 0x00000c00, + HOST_CS_SELECTOR = 0x00000c02, + HOST_SS_SELECTOR = 0x00000c04, + HOST_DS_SELECTOR = 0x00000c06, + HOST_FS_SELECTOR = 0x00000c08, + HOST_GS_SELECTOR = 0x00000c0a, + HOST_TR_SELECTOR = 0x00000c0c, + IO_BITMAP_A = 0x00002000, + IO_BITMAP_A_HIGH = 0x00002001, + IO_BITMAP_B = 0x00002002, + IO_BITMAP_B_HIGH = 0x00002003, + VM_EXIT_MSR_STORE_ADDR = 0x00002006, + VM_EXIT_MSR_STORE_ADDR_HIGH = 0x00002007, + VM_EXIT_MSR_LOAD_ADDR = 0x00002008, + VM_EXIT_MSR_LOAD_ADDR_HIGH = 0x00002009, + VM_ENTRY_MSR_LOAD_ADDR = 0x0000200a, + VM_ENTRY_MSR_LOAD_ADDR_HIGH = 0x0000200b, + TSC_OFFSET = 0x00002010, + TSC_OFFSET_HIGH = 0x00002011, + VIRTUAL_APIC_PAGE_ADDR = 0x00002012, + VIRTUAL_APIC_PAGE_ADDR_HIGH = 0x00002013, + VMCS_LINK_POINTER = 0x00002800, + VMCS_LINK_POINTER_HIGH = 0x00002801, + GUEST_IA32_DEBUGCTL = 0x00002802, + GUEST_IA32_DEBUGCTL_HIGH = 0x00002803, + PIN_BASED_VM_EXEC_CONTROL = 0x00004000, + CPU_BASED_VM_EXEC_CONTROL = 0x00004002, + EXCEPTION_BITMAP = 0x00004004, + PAGE_FAULT_ERROR_CODE_MASK = 0x00004006, + PAGE_FAULT_ERROR_CODE_MATCH = 0x00004008, + CR3_TARGET_COUNT = 0x0000400a, + VM_EXIT_CONTROLS = 0x0000400c, + VM_EXIT_MSR_STORE_COUNT = 0x0000400e, + VM_EXIT_MSR_LOAD_COUNT = 0x00004010, + VM_ENTRY_CONTROLS = 0x00004012, + VM_ENTRY_MSR_LOAD_COUNT = 0x00004014, + VM_ENTRY_INTR_INFO_FIELD = 0x00004016, + VM_ENTRY_EXCEPTION_ERROR_CODE = 0x00004018, + VM_ENTRY_INSTRUCTION_LEN = 0x0000401a, + TPR_THRESHOLD = 0x0000401c, + SECONDARY_VM_EXEC_CONTROL = 0x0000401e, + VM_INSTRUCTION_ERROR = 0x00004400, + VM_EXIT_REASON = 0x00004402, + VM_EXIT_INTR_INFO = 0x00004404, + VM_EXIT_INTR_ERROR_CODE = 0x00004406, + IDT_VECTORING_INFO_FIELD = 0x00004408, + IDT_VECTORING_ERROR_CODE = 0x0000440a, + VM_EXIT_INSTRUCTION_LEN = 0x0000440c, + VMX_INSTRUCTION_INFO = 0x0000440e, + GUEST_ES_LIMIT = 0x00004800, + GUEST_CS_LIMIT = 0x00004802, + GUEST_SS_LIMIT = 0x00004804, + GUEST_DS_LIMIT = 0x00004806, + GUEST_FS_LIMIT = 0x00004808, + GUEST_GS_LIMIT = 0x0000480a, + GUEST_LDTR_LIMIT = 0x0000480c, + GUEST_TR_LIMIT = 0x0000480e, + GUEST_GDTR_LIMIT = 0x00004810, + GUEST_IDTR_LIMIT = 0x00004812, + GUEST_ES_AR_BYTES = 0x00004814, + GUEST_CS_AR_BYTES = 0x00004816, + GUEST_SS_AR_BYTES = 0x00004818, + GUEST_DS_AR_BYTES = 0x0000481a, + GUEST_FS_AR_BYTES = 0x0000481c, + GUEST_GS_AR_BYTES = 0x0000481e, + GUEST_LDTR_AR_BYTES = 0x00004820, + GUEST_TR_AR_BYTES = 0x00004822, + GUEST_INTERRUPTIBILITY_INFO = 0x00004824, + GUEST_ACTIVITY_STATE = 0x00004826, + GUEST_SYSENTER_CS = 0x0000482A, + HOST_IA32_SYSENTER_CS = 0x00004c00, + CR0_GUEST_HOST_MASK = 0x00006000, + CR4_GUEST_HOST_MASK = 0x00006002, + CR0_READ_SHADOW = 0x00006004, + CR4_READ_SHADOW = 0x00006006, + CR3_TARGET_VALUE0 = 0x00006008, + CR3_TARGET_VALUE1 = 0x0000600a, + CR3_TARGET_VALUE2 = 0x0000600c, + CR3_TARGET_VALUE3 = 0x0000600e, + EXIT_QUALIFICATION = 0x00006400, + GUEST_LINEAR_ADDRESS = 0x0000640a, + GUEST_CR0 = 0x00006800, + GUEST_CR3 = 0x00006802, + GUEST_CR4 = 0x00006804, + GUEST_ES_BASE = 0x00006806, + GUEST_CS_BASE = 0x00006808, + GUEST_SS_BASE = 0x0000680a, + GUEST_DS_BASE = 0x0000680c, + GUEST_FS_BASE = 0x0000680e, + GUEST_GS_BASE = 0x00006810, + GUEST_LDTR_BASE = 0x00006812, + GUEST_TR_BASE = 0x00006814, + GUEST_GDTR_BASE = 0x00006816, + GUEST_IDTR_BASE = 0x00006818, + GUEST_DR7 = 0x0000681a, + GUEST_RSP = 0x0000681c, + GUEST_RIP = 0x0000681e, + GUEST_RFLAGS = 0x00006820, + GUEST_PENDING_DBG_EXCEPTIONS = 0x00006822, + GUEST_SYSENTER_ESP = 0x00006824, + GUEST_SYSENTER_EIP = 0x00006826, + HOST_CR0 = 0x00006c00, + HOST_CR3 = 0x00006c02, + HOST_CR4 = 0x00006c04, + HOST_FS_BASE = 0x00006c06, + HOST_GS_BASE = 0x00006c08, + HOST_TR_BASE = 0x00006c0a, + HOST_GDTR_BASE = 0x00006c0c, + HOST_IDTR_BASE = 0x00006c0e, + HOST_IA32_SYSENTER_ESP = 0x00006c10, + HOST_IA32_SYSENTER_EIP = 0x00006c12, + HOST_RSP = 0x00006c14, + HOST_RIP = 0x00006c16, +}; + +enum guest_activity_state { + GUEST_STATE_ACTIVE = 0, + GUEST_STATE_HALT = 1, + GUEST_STATE_SHUTDOWN = 2, + GUEST_STATE_WAIT_SIPI = 3, +}; + +#define VMCALL_OPCODE ".byte 0x0f,0x01,0xc1\n" +#define VMCLEAR_OPCODE ".byte 0x66,0x0f,0xc7\n" /* reg/opcode: /6 */ +#define VMLAUNCH_OPCODE ".byte 0x0f,0x01,0xc2\n" +#define VMPTRLD_OPCODE ".byte 0x0f,0xc7\n" /* reg/opcode: /6 */ +#define VMPTRST_OPCODE ".byte 0x0f,0xc7\n" /* reg/opcode: /7 */ +#define VMREAD_OPCODE ".byte 0x0f,0x78\n" +#define VMRESUME_OPCODE ".byte 0x0f,0x01,0xc3\n" +#define VMWRITE_OPCODE ".byte 0x0f,0x79\n" +#define VMXOFF_OPCODE ".byte 0x0f,0x01,0xc4\n" +#define VMXON_OPCODE ".byte 0xf3,0x0f,0xc7\n" + +#define MODRM_EAX_06 ".byte 0x30\n" /* [EAX], with reg/opcode: /6 */ +#define MODRM_EAX_07 ".byte 0x38\n" /* [EAX], with reg/opcode: /7 */ +#define MODRM_EAX_ECX ".byte 0xc1\n" /* [EAX], [ECX] */ + +/* + * Exit Reasons + */ +#define VMX_EXIT_REASONS_FAILED_VMENTRY 0x80000000 + +#define EXIT_REASON_INIT 3 +#define EXIT_REASON_SIPI 4 +#define EXIT_REASON_VMCALL 18 +#define EXIT_REASON_INVALID_GUEST_STATE 33 +#define EXIT_REASON_MSR_LOADING 34 +#define EXIT_REASON_MACHINE_CHECK 41 + +static inline void __vmptrld(uint64_t addr) +{ + /* TBD: do not crash on failure */ + __asm__ __volatile__ ( VMPTRLD_OPCODE + MODRM_EAX_06 + /* CF==1 or ZF==1 --> crash (ud2) */ + "ja 1f ; ud2 ; 1:\n" + : + : "a" (&addr) + : "memory"); +} + +static inline void __vmptrst(uint64_t addr) +{ + __asm__ __volatile__ ( VMPTRST_OPCODE + MODRM_EAX_07 + : + : "a" (&addr) + : "memory"); +} + +static inline void __vmpclear(uint64_t addr) +{ + /* TBD: do not crash on failure */ + __asm__ __volatile__ ( VMCLEAR_OPCODE + MODRM_EAX_06 + /* CF==1 or ZF==1 --> crash (ud2) */ + "ja 1f ; ud2 ; 1:\n" + : + : "a" (&addr) + : "memory"); +} + +static inline unsigned long __vmread(unsigned long field) +{ + unsigned long ecx; + + /* TBD: do not crash on failure */ + __asm__ __volatile__ ( VMREAD_OPCODE + MODRM_EAX_ECX + /* CF==1 or ZF==1 --> crash (ud2) */ + "ja 1f ; ud2 ; 1:\n" + : "=c" (ecx) + : "a" (field) + : "memory"); + + return ecx; +} + +static inline void __vmwrite(unsigned long field, unsigned long value) +{ + /* TBD: do not crash on failure */ + __asm__ __volatile__ ( VMWRITE_OPCODE + MODRM_EAX_ECX + /* CF==1 or ZF==1 --> crash (ud2) */ + "ja 1f ; ud2 ; 1:\n" + : + : "a" (field) , "c" (value) + : "memory"); +} + +static inline void __vmlaunch (void) +{ + __asm__ __volatile__ ( VMLAUNCH_OPCODE + ::: "memory"); +} + +static inline void __vmresume (void) +{ + __asm__ __volatile__ ( VMRESUME_OPCODE + ::: "memory"); +} + +static inline void __vmxoff (void) +{ + __asm__ __volatile__ ( VMXOFF_OPCODE + ::: "memory"); +} + +static inline int __vmxon (uint64_t addr) +{ + int rc; + + __asm__ __volatile__ ( VMXON_OPCODE + MODRM_EAX_06 + /* CF==1 or ZF==1 --> rc = -1 */ + "setna %b0 ; neg %0" + : "=q" (rc) + : "0" (0), "a" (&addr) + : "memory"); + + return rc; +} + +void handle_init_sipi_sipi(unsigned int cpuid); +void force_aps_exit(void); +void init_vmcs_addrs(void); + +struct mutex ap_lock; + +#endif /* __TXT_VMCS_H__ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/types.h b/tboot/include/types.h new file mode 100644 index 0000000..f6fb7a2 --- /dev/null +++ b/tboot/include/types.h @@ -0,0 +1,104 @@ +/* + * types.h: defines size-based types for 32b builds + * + * Copyright (c) 2010, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __TYPES_H__ +#define __TYPES_H__ + +/* Need for other later defines. */ +#include + +#ifndef NULL +#define NULL ((void*)0) +#endif + +#if !defined(__GNUC__) +typedef unsigned char uint8_t; +typedef unsigned short uint16_t; +typedef unsigned int uint32_t; +#endif + +typedef unsigned char u8; +typedef unsigned short u16; +typedef unsigned int u32; + +typedef signed short s16; + +typedef unsigned char u_char; + +typedef unsigned int u_int; + +typedef unsigned char u_int8_t; +typedef unsigned short u_int16_t; +typedef unsigned int u_int32_t; + +/* + * This should be unsigned int but gets an error in + * policy.c that expects it to be an unsigned long. + */ +/* TODO building for x64 now */ +typedef unsigned long long size_t; + +typedef uint16_t wchar_t; + +/* + * This is specifically for IA32. + */ +/* TODO building for x64 now */ +#if !defined(__GNUC__) +typedef unsigned long long uintptr_t; +typedef unsigned long long uint64_t; +#endif +typedef unsigned long long u64; +typedef unsigned long long u_int64_t; + +#define BYTES_PER_LONG 4 + +#if __GNUC__ > 3 +#define offsetof(type, field) __builtin_offsetof(type, field) +#else +#define offsetof(type, member) ((size_t) &((type *)0)->member) +#endif + +#endif /* __TYPES_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/uuid.h b/tboot/include/uuid.h new file mode 100644 index 0000000..256bd02 --- /dev/null +++ b/tboot/include/uuid.h @@ -0,0 +1,82 @@ +/* + * uuid.h: support functions for UUIDs + * + * Copyright (c) 2006-2007, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __UUID_H__ +#define __UUID_H__ + +typedef struct __packed { + uint32_t data1; + uint16_t data2; + uint16_t data3; + uint16_t data4; + uint8_t data5[6]; +} uuid_t; + +static inline bool are_uuids_equal(const uuid_t *uuid1, const uuid_t *uuid2) +{ + return (memcmp(uuid1, uuid2, sizeof(*uuid1)) == 0); +} + +#ifndef PRINT +#define PRINT printk +#endif + +#ifndef TBOOT_DETA +#define TBOOT_DETA "<4>" +#endif + +static inline void print_uuid(const uuid_t *uuid) +{ + PRINT(TBOOT_DETA"{0x%08x, 0x%04x, 0x%04x, 0x%04x,\n" + "\t\t{0x%02x, 0x%02x, 0x%02x, 0x%02x, 0x%02x, 0x%02x}}", + uuid->data1, (uint32_t)uuid->data2, (uint32_t)uuid->data3, + (uint32_t)uuid->data4, (uint32_t)uuid->data5[0], + (uint32_t)uuid->data5[1], (uint32_t)uuid->data5[2], + (uint32_t)uuid->data5[3], (uint32_t)uuid->data5[4], + (uint32_t)uuid->data5[5]); +} + +#endif /* __UUID_H__ */ + + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/vga.h b/tboot/include/vga.h new file mode 100644 index 0000000..7e9914a --- /dev/null +++ b/tboot/include/vga.h @@ -0,0 +1,87 @@ +/* + * vga.h: definitions of and supports functions for VGA + * + * Copyright (c) 2006-2010, Intel Corporation + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following + * disclaimer in the documentation and/or other materials provided + * with the distribution. + * * Neither the name of the Intel Corporation nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef __VGA_H__ +#define __VGA_H__ + +#define VGA_BASE 0xb8000 + +/* 80*25 text mode*/ +#define MAX_LINES 25 +#define MAX_COLS 80 +#define SCREEN_BUFFER (MAX_LINES*MAX_COLS*2) +#define VGA_ADDR(x, y) (VGA_BASE + 2*(MAX_COLS*(y) + (x))) + +/* registers */ +#define CTL_ADDR_REG 0x3D4 +#define CTL_DATA_REG 0x3D5 +#define START_ADD_HIGH_REG 0x0C +#define START_ADD_LOW_REG 0x0D + +/* colors */ +#define COLOR_BLACK 0x00 +#define COLOR_BLUE 0x01 +#define COLOR_GREEN 0x02 +#define COLOR_CYAN 0x03 +#define COLOR_RED 0x04 +#define COLOR_MAGENTA 0x05 +#define COLOR_BROWN 0x06 +#define COLOR_LTGRAY 0x07 +#define COLOR_DKGRAY 0x08 +#define COLOR_LTBLUE 0x09 +#define COLOR_LTGREEN 0x0A +#define COLOR_LTCYAN 0x0B +#define COLOR_LTRED 0x0C +#define COLOR_LTMAGENTA 0x0D +#define COLOR_LTBROWN 0x0E +#define COLOR_WHITE 0x0F + +#define COLOR ((COLOR_BLACK << 4) | COLOR_LTGRAY) + + +void vga_init(void); +void vga_puts(const char *s, unsigned int cnt); + +#endif /* __VGA_H__ */ + +/* + * Local variables: + * mode: C + * c-set-style: "BSD" + * c-basic-offset: 4 + * tab-width: 4 + * indent-tabs-mode: nil + * End: + */ diff --git a/tboot/include/vmac.h b/tboot/include/vmac.h new file mode 100644 index 0000000..6104668 --- /dev/null +++ b/tboot/include/vmac.h @@ -0,0 +1,168 @@ +#ifndef HEADER_VMAC_H +#define HEADER_VMAC_H + +/* -------------------------------------------------------------------------- + * VMAC and VHASH Implementation by Ted Krovetz (tdk@acm.org) and Wei Dai. + * This implementation is herby placed in the public domain. + * The authors offers no warranty. Use at your own risk. + * Please send bug reports to the authors. + * Last modified: 17 APR 08, 1700 PDT + * ----------------------------------------------------------------------- */ + +/* -------------------------------------------------------------------------- + * User definable settings. + * ----------------------------------------------------------------------- */ +#define VMAC_TAG_LEN 64 /* Must be 64 or 128 - 64 sufficient for most */ +#define VMAC_KEY_LEN 128 /* Must be 128, 192 or 256 */ +#define VMAC_NHBYTES 4096/* Must 2^i for any 3 < i < 13. Standard = 128 */ +#define VMAC_PREFER_BIG_ENDIAN 0 /* Prefer non-x86 */ + +#define VMAC_USE_OPENSSL 0 /* Set to non-zero to use OpenSSL's AES */ +#define VMAC_CACHE_NONCES 1 /* Set to non-zero to cause caching */ + /* of consecutive nonces on 64-bit tags */ + +#define VMAC_RUN_TESTS 0 /* Set to non-zero to check vectors and speed */ +#define VMAC_HZ (448e6) /* Set to hz of host machine to get speed */ +#define VMAC_HASH_ONLY 0 /* Set to non-zero to time hash only (not-mac) */ +/* Speeds of cpus I have access to +#define hz (2400e6) glyme Core 2 "Conroe" +#define hz (2000e6) jupiter G5 +#define hz (1592e6) titan +#define hz (2793e6) athena/gaia +#define hz (1250e6) isis G4 +#define hz (2160e6) imac Core 2 "Merom" +#define hz (266e6) ppc/arm +#define hz (400e6) mips +*/ + +/* -------------------------------------------------------------------------- + * This implementation uses uint32_t and uint64_t as names for unsigned 32- + * and 64-bit integer types. These are defined in C99 stdint.h. The + * following may need adaptation if you are not running a C99 or + * Microsoft C environment. + * ----------------------------------------------------------------------- */ +#define VMAC_USE_STDINT 1 /* Set to zero if system has no stdint.h */ + +#if VMAC_USE_STDINT && !_MSC_VER /* Try stdint.h if non-Microsoft */ +//#include +#elif (_MSC_VER) /* Microsoft C does not have stdint.h */ +typedef unsigned __int32 uint32_t; +typedef unsigned __int64 uint64_t; +#define UINT64_C(v) v ## UI64 +#else /* Guess sensibly - may need adaptation */ +typedef unsigned int uint32_t; +typedef unsigned long long uint64_t; +#define UINT64_C(v) v ## ULL +#endif + +/* -------------------------------------------------------------------------- + * This implementation supports two free AES implementations: OpenSSL's and + * Paulo Barreto's. To use OpenSSL's, you will need to include the OpenSSL + * crypto library (eg, gcc -lcrypto foo.c). For Barreto's, you will need + * to compile rijndael-alg-fst.c, last seen at http://www.iaik.tu-graz.ac.at/ + * research/krypto/AES/old/~rijmen/rijndael/rijndael-fst-3.0.zip and + * http://homes.esat.kuleuven.be/~rijmen/rijndael/rijndael-fst-3.0.zip. + * To use a different implementation, use these definitions as a model. + * ----------------------------------------------------------------------- */ +#if VMAC_USE_OPENSSL + +#include +typedef AES_KEY aes_int_key; + +#define aes_encryption(in,out,int_key) \ + AES_encrypt((unsigned char *)(in),(unsigned char *)(out),(int_key)) +#define aes_key_setup(key,int_key) \ + AES_set_encrypt_key((key),VMAC_KEY_LEN,(int_key)) + +#else + +//#include "rijndael-alg-fst.h" +typedef uint64_t vmac_t; +#include "rijndael.h" +typedef u32 aes_int_key[4*(VMAC_KEY_LEN/32+7)]; + +#define aes_encryption(in,out,int_key) \ + rijndaelEncrypt((u32 *)(int_key), \ + ((VMAC_KEY_LEN/32)+6), \ + (u8 *)(in), (u8 *)(out)) +#define aes_key_setup(user_key,int_key) \ + rijndaelKeySetupEnc((u32 *)(int_key), \ + (u8 *)(user_key), \ + VMAC_KEY_LEN) +#endif + +/* --------------------------------------------------------------------- */ + +typedef struct { + uint64_t nhkey [(VMAC_NHBYTES/8)+2*(VMAC_TAG_LEN/64-1)]; + uint64_t polykey[2*VMAC_TAG_LEN/64]; + uint64_t l3key [2*VMAC_TAG_LEN/64]; + uint64_t polytmp[2*VMAC_TAG_LEN/64]; + aes_int_key cipher_key; + #if (VMAC_TAG_LEN == 64) && (VMAC_CACHE_NONCES) + uint64_t cached_nonce[2]; + uint64_t cached_aes[2]; + #endif + int first_block_processed; +} vmac_ctx_t; + +/* --------------------------------------------------------------------- */ +/* -------------------------------------------------------------------------- + * <<<<< USAGE NOTES >>>>> + * + * Given msg m (mbytes in length) and nonce buffer n + * this function returns a tag as its output. The tag is returned as + * a number. When VMAC_TAG_LEN == 64, the 'return'ed integer is the tag, + * and *tagl is meaningless. When VMAC_TAG_LEN == 128 the tag is the + * number y * 2^64 + *tagl where y is the function's return value. + * If you want to consider tags to be strings, then you must do so with + * an agreed upon endian orientation for interoperability, and convert + * the results appropriately. VHASH hashes m without creating any tag. + * Consecutive substrings forming a prefix of a message may be passed + * to vhash_update, with vhash or vmac being called with the remainder + * to produce the output. + * + * Requirements: + * - On 32-bit architectures with SSE2 instructions, ctx and m MUST be + * begin on 16-byte memory boundaries. + * - m MUST be your message followed by zeroes to the nearest 16-byte + * boundary. If m is a length multiple of 16 bytes, then it is already + * at a 16-byte boundary and needs no padding. mbytes should be your + * message length without any padding. + * - The first bit of the nonce buffer n must be 0. An i byte nonce, is made + * as the first 16-i bytes of n being zero, and the final i the nonce. + * - vhash_update MUST have mbytes be a positive multiple of VMAC_NHBYTES + * ----------------------------------------------------------------------- */ + +#define vmac_update vhash_update + +void vhash_update(unsigned char m[], + unsigned int mbytes, + vmac_ctx_t *ctx); + +uint64_t vmac(unsigned char m[], + unsigned int mbytes, + unsigned char n[16], + uint64_t *tagl, + vmac_ctx_t *ctx); + +uint64_t vhash(unsigned char m[], + unsigned int mbytes, + uint64_t *tagl, + vmac_ctx_t *ctx); + +/* -------------------------------------------------------------------------- + * When passed a VMAC_KEY_LEN bit user_key, this function initialazies ctx. + * ----------------------------------------------------------------------- */ + +void vmac_set_key(unsigned char user_key[], vmac_ctx_t *ctx); + +/* -------------------------------------------------------------------------- + * This function aborts current hash and resets ctx, ready for a new message. + * ----------------------------------------------------------------------- */ + +void vhash_abort(vmac_ctx_t *ctx); + +/* --------------------------------------------------------------------- */ + +#endif /* HEADER_AES_H */ -- cgit v1.2.3