Merge remote-tracking branch 'upstream/master' into system76_cleanup

This commit is contained in:
Jeremy Soller
2019-05-10 17:35:18 -06:00
317 changed files with 4637 additions and 2415 deletions

2
3rdparty/vboot vendored

View File

@@ -29,7 +29,6 @@
</li>
<li><a target="_blank" href="SoC/soc.html">SoC</a> support</li>
<li><a target="_blank" href="Board/board.html">Board</a> support</li>
<li><a target="_blank" href="vboot.html">Verified Boot (vboot)</a> support</li>
</ul>

View File

@@ -1,402 +0,0 @@
<!DOCTYPE html>
<html>
<head>
<title>vboot - Verified Boot Support</title>
</head>
<body>
<h1>vboot - Verified Boot Support</h1>
<p>
Google's verified boot support consists of:
</p>
<ul>
<li>A root of trust</li>
<li>Special firmware layout</li>
<li>Firmware verification</li>
<li>Firmware measurements</li>
<li>A firmware update mechanism</li>
<li>Specific build flags</li>
<li>Signing the coreboot image</li>
</ul>
Google's vboot verifies the firmware and places measurements
within the TPM.
<hr>
<h2>Root of Trust</h2>
<p>
When using vboot, the root-of-trust is basically the read-only portion of the
SPI flash. The following items factor into the trust equation:
</p>
<ul>
<li>The GCC compiler must reliably translate the code into machine code
without inserting any additional code (virus, backdoor, etc.)
</li>
<li>The CPU must reliably execute the reset sequence and instructions as
documented by the CPU manufacturer.
</li>
<li>The SPI flash must provide only the code programmed into it to the CPU
without providing any alternative reset vector or code sequence.
</li>
<li>The SPI flash must honor the write-protect input and protect the
specified portion of the SPI flash from all erase and write accesses.
</li>
</ul>
<p>
The firmware is typically protected using the write-protect pin on the SPI
flash part and setting some of the write-protect bits in the status register
during manufacturing. The protected area is platform specific and for x86
platforms is typically 1/4th of the SPI flash
part size. Because this portion of the SPI flash is hardware write protected,
it is not possible to update this portion of the SPI flash in the field,
without altering the system to eliminate the ground connection to the SPI flash
write-protect pin. Without hardware modifications, this portion of the SPI
flash maintains the manufactured state during the system's lifetime.
</p>
<hr>
<h2>Firmware Layout</h2>
<p>
Several sections are added to the firmware layout to support vboot:
</p>
<ul>
<li>Read-only section</li>
<li>Google Binary Blob (GBB) area</li>
<li>Read/write section A</li>
<li>Read/write section B</li>
</ul>
<p>
The following sections describe the various portions of the flash layout.
</p>
<h3>Read-Only Section</h3>
<p>
The read-only section contains a coreboot file system (CBFS) that contains all
of the boot firmware necessary to perform recovery for the system. This
firmware is typically protected using the write-protect pin on the SPI flash
part and setting some of the write-protect bits in the status register during
manufacturing. The protected area is typically 1/4th of the SPI flash part
size and must cover the entire read-only section which consists of:
</p>
<ul>
<li>Vital Product Data (VPD) area</li>
<li>Firmware ID area</li>
<li>Google Binary Blob (GBB) area</li>
<li>coreboot file system containing read-only recovery firmware</li>
</ul>
<h3>Google Binary Blob (GBB) Area</h3>
<p>
The GBB area is part of the read-only section. This area contains a 4096 or
8192 bit public root RSA key that is used to verify the VBLOCK area to obtain
the firmware signing key.
</p>
<h3>Recovery Firmware</h3>
<p>
The recovery firmware is contained within a coreboot file system and consists
of:
</p>
<ul>
<li>reset vector</li>
<li>bootblock</li>
<li>verstage</li>
<li>romstage</li>
<li>postcar</li>
<li>ramstage</li>
<li>payload</li>
<li>flash map file</li>
<li>config file</li>
<li>processor specific files:
<ul>
<li>Microcode</li>
<li>fspm.bin</li>
<li>fsps.bin</li>
</ul>
</li>
</ul>
<p>
The recovery firmware is written during manufacturing and typically contains
code to write the storage device (eMMC device or hard disk). The recovery
image is usually contained on a socketed device such as a USB flash drive or
an SD card. Depending upon the payload firmware doing the recovery, it may
be possible for the user to interact with the system to specify the recovery
image path. Part of the recovery is also to write the A and B areas of the
SPI flash device to boot the system.
</p>
<h3>Read/Write Section</h3>
<p>
The read/write sections contain an area which contains the firmware signing
key and signature and an area containing a coreboot file system with a subset
of the firmware. The firmware files in FW_MAIN_A and FW_MAIN_B are:
</p>
<ul>
<li>romstage</li>
<li>postcar</li>
<li>ramstage</li>
<li>payload</li>
<li>config file</li>
<li>processor specific files:
<ul>
<li>Microcode</li>
<li>fspm.bin</li>
<li>fsps.bin</li>
</ul>
</li>
</ul>
<p>
The firmware subset enables most issues to be fixed in the field with firmware
updates. The firmware files handle memory and most of silicon initialization.
These files also produce the tables which get passed to the operating system.
</p>
<hr>
<h2>Firmware Updates</h2>
<p>
The read/write sections exist in one of three states:
</p>
<ul>
<li>Invalid</li>
<li>Ready to boot</li>
<li>Successfully booted</li>
</ul>
<table border="1">
<tr bgcolor="#ffc0c0">
<td>
Where is this state information written?
<br/>CMOS?
<br/>RW_NVRAM?
<br/>RW_FWID_*
</td>
</tr>
</table>
<p>
Firmware updates are handled by the operating system by writing any read/write
section that is not in the "successfully booted" state. Upon the next reboot,
vboot determines the section to boot. If it finds one in the "ready to boot"
state then it attempts to boot using that section. If the boot fails then
vboot marks the section as invalid and attempts to fall back to a read/write
section in the "successfully booted" state. If vboot is not able to find a
section in the "successfully booted" state then vboot enters recovery mode.
</p>
<p>
Only the operating system is able to transition a section from the "ready to
boot" state to the "successfully booted" state. The transition is typically
done after the operating system has been running for a while indicating
that successful boot was possible and the operating system is stable.
</p>
<p>
Note that as long as the SPI write protection is in place then the system is
always recoverable. If the flash update fails then the system will continue
to boot using the previous read/write area. The same is true if coreboot
passes control to the payload or the operating system and then the boot fails.
In the worst case, the SPI flash gets totally corrupted in which case vboot
fails the signature checks and enters recovery mode. There are no times where
the SPI flash is exposed and the reset vector or part of the recovery firmware
gets corrupted.
</p>
<hr>
<h2>Build Flags</h2>
<p>
The following Kconfig values need to be selected to enable vboot:
</p>
<ul>
<li>COLLECT_TIMESTAMPS</li>
<li>VBOOT</li>
</ul>
<p>
The starting stage needs to be specified by selecting either
VBOOT_STARTS_IN_BOOTBLOCK or VBOOT_STARTS_IN_ROMSTAGE.
</p>
<p>
If vboot starts in bootblock then vboot may be built as a separate stage by
selecting VBOOT_SEPARATE_VERSTAGE. Additionally, if static RAM is too small
to fit both verstage and romstage then selecting VBOOT_RETURN_FROM_VERSTAGE
enables bootblock to reuse the RAM occupied by verstage for romstage.
</p>
<p>
Non-volatile flash is needed for vboot operation. This flash area may be in
CMOS, the EC, or in a read/write area of the SPI flash device. Select one of
the following:
</p>
<ul>
<li>VBOOT_VBNV_CMOS</li>
<li>VBOOT_VBNV_EC</li>
<li>VBOOT_VBNV_FLASH</li>
</ul>
<p>
More non-volatile storage features may be found in src/vboot/Kconfig.
</p>
<p>
A TPM is also required for vboot operation. TPMs are available in
drivers/i2c/tpm and drivers/pc80/tpm.
</p>
<p>
In addition to adding the coreboot files into the read-only region, enabling
vboot causes the build script to add the read/write files into coreboot file
systems in FW_MAIN_A and FW_MAIN_B.
</p>
<hr>
<h2>Signing the coreboot Image</h2>
<p>
The following command script is an example of how to sign the coreboot image file.
This script is used on the Intel Galileo board and creates the GBB area and
inserts it into the coreboot image. It also updates the VBLOCK areas with the
firmware signing key and the signature for the FW_MAIN firmware. More details
are available in 3rdparty/vboot/README.
</p>
<pre><code>#!/bin/sh
#
# The necessary tools were built and installed using the following commands:
#
# pushd 3rdparty/vboot
# make
# sudo make install
# popd
#
# The keys were made using the following command
#
# 3rdparty/vboot/scripts/keygeneration/create_new_keys.sh \
# --4k --4k-root --output $PWD/keys
#
#
# The "magic" numbers below are derived from the GBB section in
# src/mainboard/intel/galileo/vboot.fmd.
#
# GBB Header Size: 0x80
# GBB Offset: 0x611000, 4KiB block number: 1553 (0x611)
# GBB Length: 0x7f000, 4KiB blocks: 127 (0x7f)
# COREBOOT Offset: 0x690000, 4KiB block number: 1680 (0x690)
# COREBOOT Length: 0x170000, 4KiB blocks: 368 (0x170)
#
# 0x7f000 (GBB Length) = 0x80 + 0x100 + 0x1000 + 0x7ce80 + 0x1000
#
# Create the GBB area blob
# Parameters: hwid_size,rootkey_size,bmpfv_size,recoverykey_size
#
gbb_utility -c 0x100,0x1000,0x7ce80,0x1000 gbb.blob
#
# Copy from the start of the flash to the GBB region into the signed flash
# image.
#
# 1553 * 4096 = 0x611 * 0x1000 = 0x611000, size of area before GBB
#
dd conv=fdatasync ibs=4096 obs=4096 count=1553 \
if=build/coreboot.rom of=build/coreboot.signed.rom
#
# Append the empty GBB area to the coreboot.rom image.
#
# 1553 * 4096 = 0x611 * 0x1000 = 0x611000, offset to GBB
#
dd conv=fdatasync obs=4096 obs=4096 seek=1553 if=gbb.blob \
of=build/coreboot.signed.rom
#
# Append the rest of the read-only region into the signed flash image.
#
# 1680 * 4096 = 0x690 * 0x1000 = 0x690000, offset to COREBOOT area
# 368 * 4096 = 0x170 * 0x1000 = 0x170000, length of COREBOOT area
#
dd conv=fdatasync ibs=4096 obs=4096 skip=1680 seek=1680 count=368 \
if=build/coreboot.rom of=build/coreboot.signed.rom
#
# Insert the HWID and public root and recovery RSA keys into the GBB area.
#
gbb_utility \
--set --hwid='Galileo' \
-r $PWD/keys/recovery_key.vbpubk \
-k $PWD/keys/root_key.vbpubk \
build/coreboot.signed.rom
#
# Sign the read/write firmware areas with the private signing key and update
# the VBLOCK_A and VBLOCK_B regions.
#
3rdparty/vboot/scripts/image_signing/sign_firmware.sh \
build/coreboot.signed.rom \
$PWD/keys \
build/coreboot.signed.rom
</code></pre>
<hr>
<h2>Boot Flow</h2>
<p>
The reset vector exist in the read-only area and points to the bootblock entry
point. The only copy of the bootblock exists in the read-only area of the SPI
flash. Verstage may be part of the bootblock or a separate stage. If separate
then the bootblock loads verstage from the read-only area and transfers control
to it.
</p>
<p>
Upon first boot, verstage attempts to verify the read/write section A. It gets
the public root key from the GBB area and uses that to verify the VBLOCK area
in read-write section A. If the VBLOCK area is valid then it extracts the
firmware signing key (1024-8192 bits) and uses that to verify the FW_MAIN_A
area of read/write section A. If the verification is successful then verstage
instructs coreboot to use the coreboot file system in read/write section A for
the contents of the remaining boot firmware (romstage, postcar, ramstage and
the payload).
</p>
<p>
If verification fails for the read/write area and the other read/write area is
not valid vboot falls back to the read-only area to boot into system recovery.
</p>
<hr>
<h2>Chromebook Special Features</h2>
<p>
Google's Chromebooks have some special features:
</p>
<ul>
<li>Developer mode</li>
<li>Write-protect screw</li>
</ul>
<h3>Developer Mode</h3>
<p>
Developer mode allows the user to use coreboot to boot another operating system.
This may be a another (beta) version of Chrome OS, or another flavor of
GNU/Linux. Use of developer mode does not void the system warranty. Upon
entry into developer mode, all locally saved data on the system is lost.
This prevents someone from entering developer mode to subvert the system
security to access files on the local system or cloud.
</p>
<h3>Write Protect Screw</h3>
<p>
Chromebooks have a write-protect screw which provides the ground to the
write-protect pin of the SPI flash. Google specifically did this to allow
the manufacturing line and advanced developers to re-write the entire SPI flash
part. Once the screw is removed, any firmware may be placed on the device.
However, accessing this screw requires opening the case and voids the system
warranty!
</p>
<hr>
<p>Modified: 2 May 2017</p>
</body>
</html>

View File

@@ -70,6 +70,10 @@ The boards in this section are not real mainboards, but emulators.
- [T430 / T530 / X230 / W530 common](lenovo/xx30_series.md)
- [T431s](lenovo/t431s.md)
## MSI
- [MS-7707](msi/ms7707/ms7707.md)
## SiFive
- [SiFive HiFive Unleashed](sifive/hifive-unleashed.md)

Binary file not shown.

After

Width:  |  Height:  |  Size: 235 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 147 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 81 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 38 KiB

View File

@@ -0,0 +1,34 @@
<?xml version="1.0" encoding="UTF-8"?>
<svg width="10cm" height="8cm" version="1.1" viewBox="265 -156 186 159" xmlns="http://www.w3.org/2000/svg" xmlns:cc="http://creativecommons.org/ns#" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#">
<metadata>
<rdf:RDF>
<cc:Work rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type rdf:resource="http://purl.org/dc/dcmitype/StillImage"/>
<dc:title/>
</cc:Work>
</rdf:RDF>
</metadata>
<rect x="308" y="-152" width="49.1" height="30.5" fill="#fff"/>
<rect x="308" y="-152" width="49.1" height="30.5" fill="none" stroke="#000" stroke-width="2"/>
<text x="332.45999" y="-134.83099" fill="#000000" font-family="sans-serif" font-size="6.77px" text-anchor="middle"><tspan x="332.45999" y="-134.83099">IFD</tspan></text>
<rect x="308" y="-60.7" width="49.1" height="59.8" fill="#fff"/>
<text x="332.46002" y="-30.227913" fill="#000000" font-family="sans-serif" font-size="6.77px" text-anchor="middle"><tspan x="332.46002" y="-30.227913">BIOS</tspan></text>
<rect x="308" y="-60.7" width="49.1" height="59.8" fill="none" stroke="#000" stroke-width="2"/>
<rect x="308" y="-91.6" width="49.1" height="30.9" fill="#fff"/>
<rect x="308" y="-91.6" width="49.1" height="30.9" fill="none" stroke="#000" stroke-width="2"/>
<text x="332.45999" y="-74.099892" fill="#000000" font-family="sans-serif" font-size="6.77px" text-anchor="middle"><tspan x="332.45999" y="-74.099892">ME</tspan></text>
<rect x="308" y="-122" width="49.1" height="30.5" fill="#fff"/>
<rect x="308" y="-122" width="49.1" height="30.5" fill="none" stroke="#000" stroke-width="2"/>
<text x="332.45999" y="-104.3643" fill="#000000" font-family="sans-serif" font-size="6.77px" text-anchor="middle"><tspan x="332.45999" y="-104.3643">GBE</tspan></text>
<g font-family="sans-serif" font-size="6.77px">
<text x="265.96799" y="-149.20799"><tspan x="265.96799" y="-149.20799">0x000000</tspan></text>
<text x="266.362" y="-120.102"><tspan x="266.362" y="-120.102">0x001000</tspan></text>
<text x="266.16199" y="-88.897202"><tspan x="266.16199" y="-88.897202">0x003000</tspan></text>
<text x="266.14401" y="-59.324112"><tspan x="266.14401" y="-59.324112">0x200000</tspan></text>
<text x="266.32599" y="-1.1522589"><tspan x="266.32599" y="-1.1522589">0x400000</tspan></text>
</g>
<path d="m381-151c21 0-1.5 77.5 19.8 78.5" fill="none" stroke="#000"/>
<path d="m381-0.763c13.9 0 5.64-72 19.5-72" fill="none" stroke="#000"/>
<text x="406.12701" y="-68.513" fill="#000000" font-family="sans-serif" font-size="10.2px"><tspan x="406.12701" y="-68.513">Flash</tspan></text>
</svg>

After

Width:  |  Height:  |  Size: 2.6 KiB

View File

@@ -0,0 +1,112 @@
# MSI MS-7707 V1.1
* MSI MS-7707 V1.1 (Medion OEM Akoya P4385D MSN10014555)
* SandyBridge Intel P67 (BD82x6x)
* Winbond 25Q32BV (4MB)
* Fintek F71808A SuperIO
* Intel 82579V Gigabit
* NEC uPD720200 USB 3.0 Host Controller
* IME 7.0.4.1197
## Flash chip (Winbond 25Q32BV)
```eval_rst
+---------------------+--------------------+
| Type | Value |
+=====================+====================+
| Size | 4 MiB |
+---------------------+--------------------+
| BIOS range | 2 MiB |
+---------------------+--------------------+
| Write protection | Yes (via jumper) |
+---------------------+--------------------+
| Header | Yes (JSPI1) |
+---------------------+--------------------+
| Package | SOIC-8 |
+---------------------+--------------------+
| In circuit flashing | Yes |
+---------------------+--------------------+
| Internal flashing | Yes |
+---------------------+--------------------+
| Socketed flash | No |
+---------------------+--------------------+
| Dual BIOS feature | No |
+---------------------+--------------------+
| ME removable | Yes |
+---------------------+--------------------+
```
## Installation instructions
* The standard method is to only flash the 2MiB BIOS region. In that case it's
not needed to extract blobs from vendor firmware and internal flashing is
sufficient.
* To flash the whole chip (e.g. to disable ME) blobs are needed to build
coreboot. Blobs can be extracted with util/ifdtool from 4MiB full dump image
(see below). Its recommended to include the VGA BIOS as well (4MiB write only).
Kconfig is prepared already if it gets enabled (path and 8086,0102).
```
coreboot/3rdparty/blobs/mainboard/msi/ms7707
├── descriptor.bin
├── gbe.bin
├── me.bin
└── vgabios.bin
```
* Never write a full 4MiB image if blobs are not included. The generated
coreboot.rom file is always 4MiB but the 2MiB flash command below will only
flash the last 2MiB (BIOS) block.
* The J1-Jumper sets the 'Flash Descriptor Override Strap-Pin' and enables
full 4MiB access for internal flasher (read and write).
* **Write BIOS-range** (2MiB) with J1-Jumper=off (as on picture/default
position):
```
flashrom -p internal:ich_spi_force=yes --noverify-all --ifd -i bios -w coreboot.rom
```
* **Read full dump** (4MiB) with J1-jumper=on:
```
flashrom -p internal -r original.rom
```
* **Write full dump** (4MiB) with J1-Jumper=on:
```
flashrom -p internal -w coreboot.rom
```
* After successful flashing turn main power off, wait some seconds to drain
the capacitors, pull the battery and set the JBAT (clrcmos) jumper for some
seconds. Setting the jumper alone is not enough (the Fintek is VBAT backed).
Put all back in place and restart the board. It might need 1-2 AC power cycles
to reinitialize (running at full fan speed - don't panic).
* External flashing has been tested with RPi2 without main power connected.
3.3V provided by RPi2. Read more about flashing methods [here](https://doc.coreboot.org/flash_tutorial/index.html).
* In case of going back to proprietary BIOS create/save cmos settings as early
as possible (do not leave BIOS on first start without saving settings).
The BIOS might corrupt nvram (not cmos!) and leave the system in a dead state
that needs an external flasher to revive. If stuck, reset the Fintek (see
above) and restart the system several times and/or try setting J1 to
temporarily disable ME.
![](J1-flash-protect.jpg)
* The JSPI1 header (5×2 2.0mm pitch pin header) for external flashing is
directly connected to the flash chip. Additional 3.3V to /HOLD and /WP is not
needed (internally re-routed already).
![](JSPI1-Winbond-W25Q32BVSIG.jpg)
![](JSPI1-connected.jpg)
![](JSPI1.png)
## Flash layout
* The 4MiB flashrom is divided into 4 sections:
![][flashlayout]
## Links
- [BIOS ROM]
- [Fintek F71808A datasheet]
- [Winbond 25Q32BV datasheet]
[BIOS ROM]: https://www.medion.com/de/servicebackend/_lightbox/treiber_details.php?did=9744
[Winbond 25Q32BV datasheet]: https://www.winbond.com/resource-files/w25q32bv_revi_100413_wo_automotive.pdf
[Fintek F71808A datasheet]: https://www.alldatasheet.com/datasheet-pdf/pdf/459069/FINTEK/F71808A.html
[flashlayout]: flashlayout.svg

View File

@@ -4,4 +4,5 @@ This section describes documentation about the security architecture of coreboot
## Vendor
- [Verified Boot](vboot/index.md)
- [Measured Boot](vboot/measured_boot.md)

View File

@@ -0,0 +1,324 @@
# vboot - Verified Boot Support
Google's verified boot support consists of:
* A root of trust
* Special firmware layout
* Firmware verification
* Firmware measurements
* A firmware update mechanism
* Specific build flags
* Signing the coreboot image
Google's vboot verifies the firmware and places measurements within the TPM.
***
## Root of Trust
When using vboot, the root-of-trust is basically the read-only portion of the
SPI flash. The following items factor into the trust equation:
* The GCC compiler must reliably translate the code into machine code
without inserting any additional code (virus, backdoor, etc.)
* The CPU must reliably execute the reset sequence and instructions as
documented by the CPU manufacturer.
* The SPI flash must provide only the code programmed into it to the CPU
without providing any alternative reset vector or code sequence.
* The SPI flash must honor the write-protect input and protect the specified
portion of the SPI flash from all erase and write accesses.
The firmware is typically protected using the write-protect pin on the SPI
flash part and setting some of the write-protect bits in the status register
during manufacturing. The protected area is platform specific and for x86
platforms is typically 1/4th of the SPI flash part size.
Because this portion of the SPI flash is hardware write protected, it is not
possible to update this portion of the SPI flash in the field, without altering
the system to eliminate the ground connection to the SPI flash write-protect pin.
Without hardware modifications, this portion of the SPI flash maintains the
manufactured state during the system's lifetime.
***
## Firmware Layout
Several sections are added to the firmware layout to support vboot:
* Read-only section
* Google Binary Blob (GBB) area
* Read/write section A
* Read/write section B
The following sections describe the various portions of the flash layout.
### Read-Only Section
The read-only section contains a coreboot file system (CBFS) that contains all
of the boot firmware necessary to perform recovery for the system. This firmware
is typically protected using the write-protect pin on the SPI flash part and
setting some of the write-protect bits in the status register during
manufacturing.
The protected area is typically 1/4th of the SPI flash part size and must cover
the entire read-only section which consists of:
* Vital Product Data (VPD) area
* Firmware ID area
* Google Binary Blob (GBB) area
* coreboot file system containing read-only recovery firmware
### Google Binary Blob (GBB) Area
The GBB area is part of the read-only section. This area contains a 4096 or 8192
bit public root RSA key that is used to verify the *VBLOCK* area to obtain the
firmware signing key.
### Recovery Firmware
The recovery firmware is contained within a coreboot file system and consists of:
* reset vector
* bootblock
* verstage
* romstage
* postcar
* ramstage
* payload
* flash map file
* config file
* processor specific files:
* Microcode
* fspm.bin
* fsps.bin
The recovery firmware is written during manufacturing and typically contains
code to write the storage device (eMMC device or hard disk). The recovery image
is usually contained on a socketed device such as a USB flash drive or an
SD card. Depending upon the payload firmware doing the recovery, it may be
possible for the user to interact with the system to specify the recovery
image path. Part of the recovery is also to write the A and B areas of the SPI
flash device to boot the system.
### Read/Write Section
The read/write sections contain an area which contains the firmware signing
key and signature and an area containing a coreboot file system with a subset
of the firmware. The firmware files in *FW_MAIN_A* and *FW_MAIN_B* are:
* romstage
* postcar
* ramstage
* payload
* config file
* processor specific files:
* Microcode
* fspm.bin
* fsps.bin
The firmware subset enables most issues to be fixed in the field with firmware
updates. The firmware files handle memory and most of silicon initialization.
These files also produce the tables which get passed to the operating system.
***
## Firmware Updates
The read/write sections exist in one of three states:
* Invalid
* Ready to boot
* Successfully booted
Firmware updates are handled by the operating system by writing any read/write
section that is not in the "successfully booted" state. Upon the next reboot,
vboot determines the section to boot. If it finds one in the "ready to boot"
state then it attempts to boot using that section. If the boot fails then
vboot marks the section as invalid and attempts to fall back to a read/write
section in the "successfully booted" state. If vboot is not able to find a
section in the "successfully booted" state then vboot enters recovery mode.
Only the operating system is able to transition a section from the
"ready to boot" state to the "successfully booted" state.
The transition is typically done after the operating system has been running
for a while indicating that successful boot was possible and the operating
system is stable.
Note that as long as the SPI write protection is in place then the system
is always recoverable. If the flash update fails then the system will continue
to boot using the previous read/write area. The same is true if coreboot passes
control to the payload or the operating system and then the boot fails. In the
worst case, the SPI flash gets totally corrupted in which case vboot fails the
signature checks and enters recovery mode. There are no times where the SPI
flash is exposed and the reset vector or part of the recovery firmware gets
corrupted.
***
## Build Flags
The following *Kconfig* values need to be selected to enable vboot:
* COLLECT_TIMESTAMPS
* VBOOT
The starting stage needs to be specified by selecting either
VBOOT_STARTS_IN_BOOTBLOCK or VBOOT_STARTS_IN_ROMSTAGE.
If vboot starts in bootblock then vboot may be built as a separate stage by
selecting `VBOOT_SEPARATE_VERSTAGE`. Additionally, if static RAM is too small
to fit both verstage and romstage then selecting `VBOOT_RETURN_FROM_VERSTAGE`
enables bootblock to reuse the RAM occupied by verstage for romstage.
Non-volatile flash is needed for vboot operation. This flash area may be in
CMOS, the EC, or in a read/write area of the SPI flash device.
Select one of the following:
* `VBOOT_VBNV_CMOS`
* `VBOOT_VBNV_EC`
* `VBOOT_VBNV_FLASH`
More non-volatile storage features may be found in `security/vboot/Kconfig`.
A TPM is also required for vboot operation.
TPMs are available in `drivers/i2c/tpm` and `drivers/pc80/tpm`.
In addition to adding the coreboot files into the read-only region,
enabling vboot causes the build script to add the read/write files into
coreboot file systems in *FW_MAIN_A* and *FW_MAIN_B*.
***
## Signing the coreboot Image
The following command script is an example of how to sign the coreboot image
file. This script is used on the Intel Galileo board and creates the *GBB* area
and inserts it into the coreboot image. It also updates the *VBLOCK* areas with
the firmware signing key and the signature for the *FW_MAIN* firmware.
More details are available in `3rdparty/vboot/README`.
```bash
#!/bin/sh
#
# The necessary tools were built and installed using the following commands:
#
# pushd 3rdparty/vboot
# make
# sudo make install
# popd
#
# The keys were made using the following command
#
# 3rdparty/vboot/scripts/keygeneration/create_new_keys.sh \
# --4k --4k-root --output $PWD/keys
#
#
# The "magic" numbers below are derived from the GBB section in
# src/mainboard/intel/galileo/vboot.fmd.
#
# GBB Header Size: 0x80
# GBB Offset: 0x611000, 4KiB block number: 1553 (0x611)
# GBB Length: 0x7f000, 4KiB blocks: 127 (0x7f)
# COREBOOT Offset: 0x690000, 4KiB block number: 1680 (0x690)
# COREBOOT Length: 0x170000, 4KiB blocks: 368 (0x170)
#
# 0x7f000 (GBB Length) = 0x80 + 0x100 + 0x1000 + 0x7ce80 + 0x1000
#
# Create the GBB area blob
# Parameters: hwid_size,rootkey_size,bmpfv_size,recoverykey_size
#
gbb_utility -c 0x100,0x1000,0x7ce80,0x1000 gbb.blob
#
# Copy from the start of the flash to the GBB region into the signed flash
# image.
#
# 1553 * 4096 = 0x611 * 0x1000 = 0x611000, size of area before GBB
#
dd conv=fdatasync ibs=4096 obs=4096 count=1553 \
if=build/coreboot.rom of=build/coreboot.signed.rom
#
# Append the empty GBB area to the coreboot.rom image.
#
# 1553 * 4096 = 0x611 * 0x1000 = 0x611000, offset to GBB
#
dd conv=fdatasync obs=4096 obs=4096 seek=1553 if=gbb.blob \
of=build/coreboot.signed.rom
#
# Append the rest of the read-only region into the signed flash image.
#
# 1680 * 4096 = 0x690 * 0x1000 = 0x690000, offset to COREBOOT area
# 368 * 4096 = 0x170 * 0x1000 = 0x170000, length of COREBOOT area
#
dd conv=fdatasync ibs=4096 obs=4096 skip=1680 seek=1680 count=368 \
if=build/coreboot.rom of=build/coreboot.signed.rom
#
# Insert the HWID and public root and recovery RSA keys into the GBB area.
#
gbb_utility \
--set --hwid='Galileo' \
-r $PWD/keys/recovery_key.vbpubk \
-k $PWD/keys/root_key.vbpubk \
build/coreboot.signed.rom
#
# Sign the read/write firmware areas with the private signing key and update
# the VBLOCK_A and VBLOCK_B regions.
#
3rdparty/vboot/scripts/image_signing/sign_firmware.sh \
build/coreboot.signed.rom \
$PWD/keys \
build/coreboot.signed.rom
```
***
## Boot Flow
The reset vector exist in the read-only area and points to the bootblock
entry point. The only copy of the bootblock exists in the read-only area
of the SPI flash. Verstage may be part of the bootblock or a separate stage.
If separate then the bootblock loads verstage from the read-only area and
transfers control to it.
Upon first boot, verstage attempts to verify the read/write section A.
It gets the public root key from the GBB area and uses that to verify the
*VBLOCK* area in read-write section A. If the *VBLOCK* area is valid then it
extracts the firmware signing key (1024-8192 bits) and uses that to verify
the *FW_MAIN_A* area of read/write section A. If the verification is successful
then verstage instructs coreboot to use the coreboot file system in read/write
section A for the contents of the remaining boot firmware (romstage, postcar,
ramstage and the payload).
If verification fails for the read/write area and the other read/write area is
not valid vboot falls back to the read-only area to boot into system recovery.
***
## Chromebook Special Features
Google's Chromebooks have some special features:
* Developer mode
* Write-protect screw
### Developer Mode
Developer mode allows the user to use coreboot to boot another operating system.
This may be a another (beta) version of Chrome OS, or another flavor of
GNU/Linux. Use of developer mode does not void the system warranty. Upon entry
into developer mode, all locally saved data on the system is lost.
This prevents someone from entering developer mode to subvert the system
security to access files on the local system or cloud.
### Write Protect Screw
Chromebooks have a write-protect screw which provides the ground to the
write-protect pin of the SPI flash.
Google specifically did this to allow the manufacturing line and advanced
developers to re-write the entire SPI flash part. Once the screw is removed,
any firmware may be placed on the device.
However, accessing this screw requires opening the case and voids the
system warranty!

View File

@@ -196,14 +196,11 @@ ifeq ($(CONFIG_USE_BLOBS),y)
# this is necessary because 3rdparty/blobs is update=none, and so is ignored
# unless explicitly requested and enabled through --checkout
forgetthis:=$(if $(GIT),$(shell git submodule update --init --checkout 3rdparty/blobs))
ifeq ($(CONFIG_PLATFORM_USES_FSP2_0),y)
ifeq ($(CONFIG_PLATFORM_USES_FSP1_0)$(CONFIG_PLATFORM_USES_FSP1_1)$(CONFIG_PLATFORM_USES_FSP2_0),y)
# this is necessary because 3rdparty/fsp is update=none, and so is ignored
# unless explicitly requested and enabled through --checkout
forgetthis:=$(if $(GIT),$(shell git submodule update --init --checkout 3rdparty/fsp))
endif
ifeq ($(CONFIG_PLATFORM_USES_FSP1_0),y)
ifeq ($(CONFIG_SOC_INTEL_FSP_BROADWELL_DE),y)
forgetthis:=$(if $(GIT),$(shell git submodule update --init --checkout 3rdparty/fsp))
endif
endif
endif
UPDATED_SUBMODULES:=1
COREBOOT_EXPORTS += UPDATED_SUBMODULES

View File

@@ -4,4 +4,6 @@ CONFIG_VENDOR_LENOVO=y
CONFIG_BOARD_LENOVO_T420=y
CONFIG_NATIVE_RAMINIT_IGNORE_MAX_MEM_FUSES=y
CONFIG_NATIVE_RAMINIT_IGNORE_XMP_MAX_DIMMS=y
CONFIG_VBOOT=y
CONFIG_H8_FN_KEY_AS_VBOOT_RECOVERY_SW=y
# CONFIG_INTEL_CHIPSET_LOCKDOWN is not set

View File

@@ -370,8 +370,6 @@ source "src/superio/*/*/Kconfig"
comment "Embedded Controllers"
source "src/ec/acpi/Kconfig"
source "src/ec/*/*/Kconfig"
# FIXME move to vendorcode
source "src/drivers/intel/fsp1_0/Kconfig"
source "src/southbridge/intel/common/firmware/Kconfig"
source "src/vendorcode/*/Kconfig"
@@ -1155,7 +1153,6 @@ config GENERIC_SPD_BIN
config DIMM_MAX
int
default 4
depends on GENERIC_SPD_BIN
help
Total number of memory DIMM slots available on motherboard.
It is multiplication of number of channel to number of DIMMs per

View File

@@ -999,6 +999,56 @@ static int smbios_write_type127(unsigned long *current, int handle)
return len;
}
/* Generate Type9 entries from devicetree */
static int smbios_walk_device_tree_type9(struct device *dev, int *handle,
unsigned long *current)
{
enum misc_slot_usage usage;
enum slot_data_bus_bandwidth bandwidth;
enum misc_slot_type type;
enum misc_slot_length length;
if (dev->path.type != DEVICE_PATH_PCI)
return 0;
if (!dev->smbios_slot_type && !dev->smbios_slot_data_width &&
!dev->smbios_slot_designation && !dev->smbios_slot_length)
return 0;
if (dev_is_active_bridge(dev))
usage = SlotUsageInUse;
else if (dev->enabled)
usage = SlotUsageAvailable;
else
usage = SlotUsageUnknown;
if (dev->smbios_slot_data_width)
bandwidth = dev->smbios_slot_data_width;
else
bandwidth = SlotDataBusWidthUnknown;
if (dev->smbios_slot_type)
type = dev->smbios_slot_type;
else
type = SlotTypeUnknown;
if (dev->smbios_slot_length)
length = dev->smbios_slot_length;
else
length = SlotLengthUnknown;
return smbios_write_type9(current, handle,
dev->smbios_slot_designation,
type,
bandwidth,
usage,
length,
1,
0,
dev->bus->secondary,
dev->path.pci.devfn);
}
static int smbios_walk_device_tree(struct device *tree, int *handle,
unsigned long *current)
{
@@ -1011,6 +1061,7 @@ static int smbios_walk_device_tree(struct device *tree, int *handle,
dev_name(dev));
len += dev->ops->get_smbios_data(dev, handle, current);
}
len += smbios_walk_device_tree_type9(dev, handle, current);
}
return len;
}

View File

@@ -1,21 +0,0 @@
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2010 coresystems GmbH
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; version 2 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
static void skip_romstage(void)
{
asm volatile (
"jmp __main\n"
);
}

View File

@@ -18,6 +18,7 @@
#include <commonlib/endian.h>
#include <commonlib/helpers.h>
#include <string.h>
#include <vb2_sha.h>
#if !defined(ERROR)
#define ERROR(x...) printk(BIOS_ERR, "CBFS: " x)

View File

@@ -56,8 +56,10 @@ static int number(void (*tx_byte)(unsigned char byte, void *data),
int count = 0;
#ifdef SUPPORT_64BIT_INTS
unsigned long long num = inum;
long long snum = num;
#else
unsigned long num = (long)inum;
unsigned long num = (unsigned long)inum;
long snum = (long)num;
if (num != inum) {
/* Alert user to an incorrect result by printing #^!. */
@@ -76,9 +78,9 @@ static int number(void (*tx_byte)(unsigned char byte, void *data),
c = (type & ZEROPAD) ? '0' : ' ';
sign = 0;
if (type & SIGN) {
if ((signed long long)num < 0) {
if (snum < 0) {
sign = '-';
num = -num;
num = -snum;
size--;
} else if (type & PLUS) {
sign = '+';

View File

@@ -628,7 +628,7 @@ void disable_children(struct bus *bus)
/*
* Returns true if the device is an enabled bridge that has at least
* one enabled device on its secondary bus.
* one enabled device on its secondary bus that is not of type NONE.
*/
bool dev_is_active_bridge(struct device *dev)
{
@@ -643,6 +643,9 @@ bool dev_is_active_bridge(struct device *dev)
for (link = dev->link_list; link; link = link->next) {
for (child = link->children; child; child = child->sibling) {
if (child->path.type == DEVICE_PATH_NONE)
continue;
if (child->enabled)
return 1;
}

View File

@@ -25,8 +25,14 @@ if PLATFORM_USES_FSP1_1
comment "Intel FSP 1.1"
config FSP_USE_REPO
bool "Use FSP binary from 3rdparty/fsp repo"
select HAVE_FSP_BIN
depends on SOC_INTEL_BRASWELL && !USE_GOOGLE_FSP
default y
config HAVE_FSP_BIN
bool "Should the Intel FSP binary be added to the flash image"
bool "Add Intel FSP binary to flash image"
help
Select this option to add an Intel FSP binary to
the resulting coreboot image.
@@ -34,6 +40,25 @@ config HAVE_FSP_BIN
Note: Without this binary, coreboot builds relying on the FSP
will not boot
config FSP_FILE
string
prompt "Intel FSP binary path and filename" if !FSP_USE_REPO
depends on HAVE_FSP_BIN
default "3rdparty/fsp/BraswellFspBinPkg/FspBin/BSWFSP.fd" if FSP_USE_REPO
default ""
help
The path and filename of the Intel FSP binary for this platform.
config FSP_LOC
hex "Intel FSP Binary location in CBFS"
default 0xfff6e000 if SOC_INTEL_BRASWELL && USE_GOOGLE_FSP
default 0xfff20000 if SOC_INTEL_BRASWELL
default 0xffee0000 if SOC_INTEL_SKYLAKE
help
The location in CBFS that the FSP is located. This must match the
value that is set in the FSP binary. If the FSP needs to be moved,
rebase the FSP with Intel's BCT (tool).
config CPU_MICROCODE_CBFS_LEN
hex "Microcode update region length in bytes"
default 0x0
@@ -47,19 +72,6 @@ config CPU_MICROCODE_CBFS_LOC
The location (base address) in CBFS that contains the microcode update
binary.
config FSP_FILE
string "Intel FSP binary path and filename"
help
The path and filename of the Intel FSP binary for this platform.
config FSP_LOC
hex "Intel FSP Binary location in CBFS"
default 0xffee0000
help
The location in CBFS that the FSP is located. This must match the
value that is set in the FSP binary. If the FSP needs to be moved,
rebase the FSP with Intel's BCT (tool).
config DISPLAY_HOBS
bool "Display hand-off-blocks (HOBs)"
default n

View File

@@ -24,9 +24,8 @@
* performs the final stage of initialization.
*/
#define LHLT_DELAY 0x50000 /* I/O delay between post codes on failure */
/* I/O delay between post codes on failure */
#define LHLT_DELAY 0x50000
/*
* Per FSP1.1 specs, following registers are preserved:
* EBX, EDI, ESI, EBP, MM0, MM1
@@ -165,8 +164,8 @@ halt1:
* 0x01 - FV signature, "_FVH" not present
* 0x02 - FFS GUID not present
* 0x03 - FSP INFO Header not found
* 0x04 - ImageBase does not equal CONFIG_FSP_LOC - Is the FSP rebased to
* a different location, or does it need to be?
* 0x04 - ImageBase does not equal CONFIG_FSP_LOC - Is the FSP rebased
* to a different location, or does it need to be?
* 0x05 - FSP INFO Header signature "FSPH" not found
* 0x06 - FSP Image ID is not the expected ID.
*/
@@ -181,7 +180,8 @@ halt2:
* 0x02 - FSP_INVALID_PARAMETER: Input parameters are invalid.
* 0x03 - FSP_UNSUPPORTED: The FSP calling conditions were not met.
* 0x07 - FSP_DEVICE_ERROR: Temp RAM initialization failed
* 0x0E - FSP_NOT_FOUND: No valid microcode was found in the microcode region.
* 0x0E - FSP_NOT_FOUND: No valid microcode was found in the microcode
* region.
* 0x14 - FSP_ALREADY_STARTED: Temp RAM initialization has been invoked
*/
movb $0xBB, %ah
@@ -213,7 +213,7 @@ CAR_init_params:
.long CONFIG_CPU_MICROCODE_CBFS_LOC /* Microcode Location */
.long CONFIG_CPU_MICROCODE_CBFS_LEN /* Microcode Length */
.long 0xFFFFFFFF - CONFIG_ROM_SIZE + 1 /* Firmware Location */
.long CONFIG_ROM_SIZE /* Total Firmware Length */
.long CONFIG_ROM_SIZE /* Firmware Length */
CAR_init_stack:
.long CAR_init_done

View File

@@ -18,20 +18,28 @@
#ifndef _COMMON_ROMSTAGE_H_
#define _COMMON_ROMSTAGE_H_
#include <stddef.h>
#include <stdint.h>
#include <arch/cpu.h>
#include <memory_info.h>
#include <fsp/car.h>
#include <fsp/util.h>
#include <soc/intel/common/mma.h>
#include <soc/pei_wrapper.h>
#include <soc/pm.h> /* chip_power_state */
struct romstage_params {
uint32_t fsp_version;
struct chipset_power_state *power_state;
struct pei_data *pei_data;
void *chipset_context;
/* Fast boot and S3 resume MRC data */
size_t saved_data_size;
const void *saved_data;
bool disable_saved_data;
/* New save data from MRC */
size_t data_to_save_size;
const void *data_to_save;
};
/*

View File

@@ -28,6 +28,7 @@
void raminit(struct romstage_params *params)
{
const bool s3wake = params->power_state->prev_sleep_state == ACPI_S3;
const EFI_GUID bootldr_tolum_guid = FSP_BOOTLOADER_TOLUM_HOB_GUID;
EFI_HOB_RESOURCE_DESCRIPTOR *cbmem_root;
FSP_INFO_HEADER *fsp_header;
@@ -46,7 +47,6 @@ void raminit(struct romstage_params *params)
u32 *mrc_hob;
u32 fsp_reserved_bytes;
MEMORY_INIT_UPD *original_params;
struct pei_data *pei_ptr;
EFI_STATUS status;
VPD_DATA_REGION *vpd_ptr;
UPD_DATA_REGION *upd_ptr;
@@ -80,10 +80,9 @@ void raminit(struct romstage_params *params)
/* Zero fill RT Buffer data and start populating fields. */
memset(&fsp_rt_common_buffer, 0, sizeof(fsp_rt_common_buffer));
pei_ptr = params->pei_data;
if (pei_ptr->boot_mode == ACPI_S3) {
if (s3wake) {
fsp_rt_common_buffer.BootMode = BOOT_ON_S3_RESUME;
} else if (pei_ptr->saved_data != NULL) {
} else if (params->saved_data != NULL) {
fsp_rt_common_buffer.BootMode =
BOOT_ASSUMING_NO_CONFIGURATION_CHANGES;
} else {
@@ -93,7 +92,7 @@ void raminit(struct romstage_params *params)
fsp_rt_common_buffer.BootLoaderTolumSize = cbmem_overhead_size();
/* Get any board specific changes */
fsp_memory_init_params.NvsBufferPtr = (void *)pei_ptr->saved_data;
fsp_memory_init_params.NvsBufferPtr = (void *)params->saved_data;
fsp_memory_init_params.RtBufferPtr = &fsp_rt_common_buffer;
fsp_memory_init_params.HobListPtr = &hob_list_ptr;
@@ -158,7 +157,7 @@ void raminit(struct romstage_params *params)
/* Migrate CAR data */
printk(BIOS_DEBUG, "0x%p: cbmem_top\n", cbmem_top());
if (pei_ptr->boot_mode != ACPI_S3) {
if (!s3wake) {
cbmem_initialize_empty_id_size(CBMEM_ID_FSP_RESERVED_MEMORY,
fsp_reserved_bytes);
} else if (cbmem_initialize_id_size(CBMEM_ID_FSP_RESERVED_MEMORY,
@@ -220,7 +219,7 @@ void raminit(struct romstage_params *params)
}
hob_ptr.Raw = get_next_guid_hob(&mrc_guid, hob_list_ptr);
if (hob_ptr.Raw == NULL) {
if (params->pei_data->saved_data == NULL) {
if (params->saved_data == NULL) {
printk(BIOS_ERR, "7.3: FSP_NON_VOLATILE_STORAGE_HOB missing!\n");
fsp_verification_failure = 1;
}
@@ -294,8 +293,8 @@ void raminit(struct romstage_params *params)
"Memory Configuration Data Hob not present\n");
else if (!vboot_recovery_mode_enabled()) {
/* Do not save MRC data in recovery path */
pei_ptr->data_to_save = GET_GUID_HOB_DATA(mrc_hob);
pei_ptr->data_to_save_size = ALIGN(
params->data_to_save = GET_GUID_HOB_DATA(mrc_hob);
params->data_to_save_size = ALIGN(
((u32)GET_HOB_LENGTH(mrc_hob)), 16);
}
}

View File

@@ -41,9 +41,7 @@
asmlinkage void *romstage_main(FSP_INFO_HEADER *fih)
{
void *top_of_stack;
struct pei_data pei_data;
struct romstage_params params = {
.pei_data = &pei_data,
.chipset_context = fih,
};
@@ -55,8 +53,6 @@ asmlinkage void *romstage_main(FSP_INFO_HEADER *fih)
if (CONFIG(SUPPORT_CPU_UCODE_IN_CBFS))
intel_update_microcode_from_cbfs();
memset(&pei_data, 0, sizeof(pei_data));
/* Display parameters */
if (!CONFIG(NO_MMCONF_SUPPORT))
printk(BIOS_SPEW, "CONFIG_MMCONF_BASE_ADDRESS: 0x%08x\n",
@@ -94,14 +90,11 @@ void romstage_common(struct romstage_params *params)
{
bool s3wake;
struct region_device rdev;
struct pei_data *pei_data;
post_code(0x32);
timestamp_add_now(TS_BEFORE_INITRAM);
pei_data = params->pei_data;
pei_data->boot_mode = params->power_state->prev_sleep_state;
s3wake = params->power_state->prev_sleep_state == ACPI_S3;
if (CONFIG(ELOG_BOOT_COUNT) && !s3wake)
@@ -112,9 +105,9 @@ void romstage_common(struct romstage_params *params)
post_code(0x33);
/* Check recovery and MRC cache */
params->pei_data->saved_data_size = 0;
params->pei_data->saved_data = NULL;
if (!params->pei_data->disable_saved_data) {
params->saved_data_size = 0;
params->saved_data = NULL;
if (!params->disable_saved_data) {
if (vboot_recovery_mode_enabled()) {
/* Recovery mode does not use MRC cache */
printk(BIOS_DEBUG,
@@ -124,12 +117,11 @@ void romstage_common(struct romstage_params *params)
params->fsp_version,
&rdev))) {
/* MRC cache found */
params->pei_data->saved_data_size =
region_device_sz(&rdev);
params->pei_data->saved_data = rdev_mmap_full(&rdev);
params->saved_data_size = region_device_sz(&rdev);
params->saved_data = rdev_mmap_full(&rdev);
/* Assume boot device is memory mapped. */
assert(CONFIG(BOOT_DEVICE_MEMORY_MAPPED));
} else if (params->pei_data->boot_mode == ACPI_S3) {
} else if (s3wake) {
/* Waking from S3 and no cache. */
printk(BIOS_DEBUG,
"No MRC cache found in S3 resume path.\n");
@@ -147,15 +139,15 @@ void romstage_common(struct romstage_params *params)
/* Save MRC output */
if (CONFIG(CACHE_MRC_SETTINGS)) {
printk(BIOS_DEBUG, "MRC data at %p %d bytes\n",
pei_data->data_to_save, pei_data->data_to_save_size);
if ((params->pei_data->boot_mode != ACPI_S3)
&& (params->pei_data->data_to_save_size != 0)
&& (params->pei_data->data_to_save != NULL))
printk(BIOS_DEBUG, "MRC data at %p %zu bytes\n",
params->data_to_save, params->data_to_save_size);
if (!s3wake
&& (params->data_to_save_size != 0)
&& (params->data_to_save != NULL))
mrc_cache_stash_data(MRC_TRAINING_DATA,
params->fsp_version,
params->pei_data->data_to_save,
params->pei_data->data_to_save_size);
params->data_to_save,
params->data_to_save_size);
}
/* Save DIMM information */
@@ -343,13 +335,6 @@ __weak int mrc_cache_stash_data(int type, uint32_t version,
return -1;
}
/* Transition RAM from off or self-refresh to active */
__weak void raminit(struct romstage_params *params)
{
post_code(POST_MEM_PREINIT_PREP_START);
die("ERROR - No RAM initialization specified!\n");
}
/* Display the memory configuration */
__weak void report_memory_config(void)
{

View File

@@ -310,8 +310,6 @@ static void do_fsp_memory_init(struct fsp_header *hdr, bool s3wake,
post_code(POST_FSP_MEMORY_EXIT);
timestamp_add_now(TS_FSP_MEMORY_INIT_END);
fsp_debug_after_memory_init(status);
/* Handle any errors returned by FspMemoryInit */
fsp_handle_reset(status);
if (status != FSP_SUCCESS) {
@@ -320,6 +318,13 @@ static void do_fsp_memory_init(struct fsp_header *hdr, bool s3wake,
}
do_fsp_post_memory_init(s3wake, fsp_version);
/*
* fsp_debug_after_memory_init() checks whether the end of the tolum
* region is the same as the top of cbmem, so must be called here
* after cbmem has been initialised in do_fsp_post_memory_init().
*/
fsp_debug_after_memory_init(status);
}
/* Load the binary into the memory specified by the info header. */

View File

@@ -45,9 +45,6 @@ static efi_return_status_t mp_get_processor_info(const
efi_uintn_t processor_number,
efi_processor_information *processor_info_buffer)
{
if (cpu_index() < 0)
return FSP_DEVICE_ERROR;
if (processor_info_buffer == NULL)
return FSP_INVALID_PARAMETER;
@@ -71,9 +68,6 @@ static efi_return_status_t mp_startup_all_aps(const
efi_ap_procedure procedure, efi_boolean_t ignored3,
efi_uintn_t timeout_usec, void *argument)
{
if (cpu_index() < 0)
return FSP_DEVICE_ERROR;
if (procedure == NULL)
return FSP_INVALID_PARAMETER;
@@ -91,9 +85,6 @@ static efi_return_status_t mp_startup_this_ap(const
efi_ap_procedure procedure, efi_uintn_t processor_number,
efi_uintn_t timeout_usec, void *argument)
{
if (cpu_index() < 0)
return FSP_DEVICE_ERROR;
if (processor_number > get_cpu_count())
return FSP_NOT_FOUND;

View File

@@ -39,6 +39,9 @@
#define LB_CKS_LOC 0
#endif
/* Don't warn for checking >= LB_CKS_RANGE_START even though it may be 0. */
#pragma GCC diagnostic ignored "-Wtype-limits"
#include <smp/spinlock.h>
#if (defined(__PRE_RAM__) && \

View File

@@ -339,7 +339,7 @@ int spi_flash_generic_probe(const struct spi_slave *spi,
printk(BIOS_INFO, "Manufacturer: %02x\n", *idp);
/* search the table for matches in shift and id */
for (i = 0; i < ARRAY_SIZE(flashes); ++i)
for (i = 0; i < (int)ARRAY_SIZE(flashes); ++i)
if (flashes[i].shift == shift && flashes[i].idcode == *idp) {
/* we have a match, call probe */
if (flashes[i].probe(spi, idp, flash) == 0) {

View File

@@ -32,6 +32,14 @@ config H8_HAS_BAT_TRESHOLDS_IMPL
bool
default n
config H8_FN_KEY_AS_VBOOT_RECOVERY_SW
bool "Enable Fn-Key as VBOOT recovery switch"
depends on VBOOT
default n
help
If VBOOT is enabled, press Fn-Key at power on to force a recovery mode
boot instead of regular FW_MAIN_x boot.
endif
config H8_DOCK_EARLY_INIT

View File

@@ -1,5 +1,18 @@
ifeq ($(CONFIG_EC_LENOVO_H8),y)
ramstage-y += sense.c
verstage-y += sense.c
romstage-y += sense.c
bootblock-y += sense.c
postcar-y += sense.c
smm-y += sense.c
ramstage-$(CONFIG_VBOOT) += vboot.c
verstage-$(CONFIG_VBOOT) += vboot.c
romstage-$(CONFIG_VBOOT) += vboot.c
bootblock-$(CONFIG_VBOOT) += vboot.c
postcar-$(CONFIG_VBOOT) += vboot.c
ifneq ($(filter y,$(CONFIG_H8_BEEP_ON_DEATH) $(CONFIG_H8_FLASH_LEDS_ON_DEATH)),)
romstage-y += panic.c
ramstage-y += panic.c

View File

@@ -38,6 +38,9 @@ void h8_usb_always_on(void);
void h8_mainboard_init_dock (void);
int h8_get_fn_key(void);
int h8_get_sense_ready(void);
void h8_bluetooth_enable(int on);
bool h8_bluetooth_nv_enable(void);
bool h8_has_bdc(struct device *dev);
@@ -135,8 +138,10 @@ void h8_ssdt_generator(struct device *dev);
#define H8_EVENT_FN_PRESS 0x39
#define H8_STATUS0 0x46
#define H8_STATUS0_FN_KEY_DOWN 0x01
#define H8_STATUS1 0x47
#define H8_STATUS2 0x48
#define H8_STATUS3 0x49
#define H8_EVENT_BAT0 0x4a
#define H8_EVENT_BAT0_STATE 0x4b

54
src/ec/lenovo/h8/sense.c Normal file
View File

@@ -0,0 +1,54 @@
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2018 Patrick Rudolph <siro@das-labor.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; version 2 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#include <ec/acpi/ec.h>
#include "h8.h"
/**
* Return the EC sense status register state.
*
* Observations showed the sense registers are all zero until the EC populates
* them after some time. Likely the EC sets all bits to it's valid state at
* once, but there's no prove as the firmware isn't available.
*
* Wait for any register having at least one bit set.
* Unlikely that all register will be zero after booting has finished.
*
* @return 1 if the EC provides valid data in sense status registers
*/
int h8_get_sense_ready(void)
{
static const u8 regs[] = { H8_STATUS0, H8_STATUS1, H8_STATUS2,
H8_STATUS3};
for (size_t i = 0; i < ARRAY_SIZE(regs); i++) {
if (ec_read(regs[i]))
return 1;
}
return 0;
}
/**
* Return the state of Fn key.
* Only valid if h8_get_sense_ready (see above) returns true.
*
* @return 1 if the key is pressed.
*/
int h8_get_fn_key(void)
{
return ec_read(H8_STATUS0) & H8_STATUS0_FN_KEY_DOWN;
}

55
src/ec/lenovo/h8/vboot.c Normal file
View File

@@ -0,0 +1,55 @@
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2019 Patrick Rudolph <siro@das-labor.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; version 2 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#include <ec/acpi/ec.h>
#include <bootmode.h>
#include <timer.h>
#include <delay.h>
#include "h8.h"
/**
* HACK: Use Fn-Key as recovery mode switch.
* Wait for sense register ready and read Fn-Key state.
*/
int get_recovery_mode_switch(void)
{
struct stopwatch sw;
if (!CONFIG(H8_FN_KEY_AS_VBOOT_RECOVERY_SW))
return 0;
/* Tests showed that it takes:
* - 700msec on Lenovo T500 from AC power on
* - less than 150msec on Lenovo T520 from AC power on
*/
stopwatch_init_msecs_expire(&sw, 1000);
while (!stopwatch_expired(&sw) && !h8_get_sense_ready())
mdelay(1);
if (!h8_get_sense_ready())
return 0;
return h8_get_fn_key();
}
/**
* Only used if CONFIG_CHROMEOS is set.
* Always zero as the #WP pin of the flash is tied high.
*/
int get_write_protect_state(void)
{
return 0;
}

View File

@@ -19,6 +19,12 @@
#include <arch/hlt.h>
#include <console/console.h>
/* TODO: Fix vendorcode headers to not define macros coreboot uses or to be more
properly isolated. */
#ifdef ASSERT
#undef ASSERT
#endif
/* GCC and CAR versions */
#define ASSERT(x) { \
if (!(x)) { \

View File

@@ -141,6 +141,12 @@ struct device {
#if !DEVTREE_EARLY
struct chip_operations *chip_ops;
const char *name;
#if CONFIG(GENERATE_SMBIOS_TABLES)
u8 smbios_slot_type;
u8 smbios_slot_data_width;
u8 smbios_slot_length;
const char *smbios_slot_designation;
#endif
#endif
DEVTREE_CONST void *chip_info;
};

View File

@@ -2689,6 +2689,11 @@
#define PCI_DEVICE_ID_INTEL_SPT_LP_U_BASE 0x9d43
#define PCI_DEVICE_ID_INTEL_SPT_LP_U_PREMIUM 0x9d48
#define PCI_DEVICE_ID_INTEL_SPT_LP_Y_PREMIUM 0x9d46
#define PCI_DEVICE_ID_INTEL_SPT_H_H170 0xa144
#define PCI_DEVICE_ID_INTEL_SPT_H_Z170 0xa145
#define PCI_DEVICE_ID_INTEL_SPT_H_Q170 0xa146
#define PCI_DEVICE_ID_INTEL_SPT_H_Q150 0xa147
#define PCI_DEVICE_ID_INTEL_SPT_H_B150 0xa148
#define PCI_DEVICE_ID_INTEL_SPT_H_C236 0xa150
#define PCI_DEVICE_ID_INTEL_SPT_H_PREMIUM 0xa14e
#define PCI_DEVICE_ID_INTEL_SPT_H_H110 0xa143

View File

@@ -26,7 +26,6 @@
#include <cpu/x86/lapic.h>
#include <console/console.h>
#include <cpu/x86/bist.h>
#include <halt.h>
#include <northbridge/intel/i945/i945.h>
#include <northbridge/intel/i945/raminit.h>
#include <southbridge/intel/i82801gx/i82801gx.h>

View File

@@ -12,7 +12,7 @@ config BOARD_SPECIFIC_OPTIONS
select SERIRQ_CONTINUOUS_MODE
select SOUTHBRIDGE_INTEL_BD82X6X
select SYSTEM_TYPE_LAPTOP
select GFX_GMA_INTERNAL_IS_LVDS
select GFX_GMA_INTERNAL_IS_EDP
select MAINBOARD_HAS_LIBGFXINIT
config MAINBOARD_DIR

View File

@@ -29,7 +29,6 @@
#include <console/console.h>
#include <cpu/x86/bist.h>
#include <cpu/intel/romstage.h>
#include <halt.h>
#include <northbridge/intel/i945/i945.h>
#include <northbridge/intel/i945/raminit.h>
#include <southbridge/intel/i82801gx/i82801gx.h>

View File

@@ -24,7 +24,6 @@
#include <cpu/intel/speedstep.h>
#include <cpu/x86/bist.h>
#include <cpu/x86/msr.h>
#include <halt.h>
#include <northbridge/intel/x4x/iomap.h>
#include <northbridge/intel/x4x/x4x.h>
#include <southbridge/intel/common/gpio.h>

View File

@@ -25,7 +25,6 @@
#include <console/console.h>
#include <cpu/x86/bist.h>
#include <cpu/intel/romstage.h>
#include <halt.h>
#include <northbridge/intel/i945/i945.h>
#include <northbridge/intel/i945/raminit.h>
#include <southbridge/intel/i82801gx/i82801gx.h>

View File

@@ -14,7 +14,6 @@
* GNU General Public License for more details.
*/
#include <smbios.h>
#include <types.h>
#include <arch/acpi.h>
#include <arch/io.h>
@@ -25,8 +24,8 @@
#include <device/pci_ops.h>
#include <southbridge/intel/lynxpoint/pch.h>
#include <vendorcode/google/chromeos/chromeos.h>
#include "onboard.h"
#include "onboard.h"
void mainboard_suspend_resume(void)
{

View File

@@ -24,16 +24,15 @@ FLASH@0x0 8M {
RO_FRID 0x100
}
RO_VPD(PRESERVE) 16K
# TODO(hungte): Remove RO_PRESERVE.
RO_PRESERVE(PRESERVE) {
RO_DDR_TRAINING 8K
RO_FSG
}
RO_DDR_TRAINING(PRESERVE) 8K
RO_LIMITS_CFG(PRESERVE) 4K
RO_FSG(PRESERVE)
}
RW_VPD(PRESERVE) 32K
RW_NVRAM(PRESERVE) 16K
RW_DDR_TRAINING 8K
RW_DDR_TRAINING(PRESERVE) 8K
RW_LIMITS_CFG(PRESERVE) 4K
RW_ELOG(PRESERVE) 4K
RW_SHARED 4K {
SHARED_DATA

View File

@@ -16,9 +16,23 @@
#include <device/device.h>
#include <bootblock_common.h>
#include <gpio.h>
#include <timestamp.h>
#include <soc/usb.h>
static struct usb_board_data usb1_board_data = {
.pll_bias_control_2 = 0x28,
.imp_ctrl1 = 0x08,
.port_tune1 = 0x20,
};
static void setup_usb(void)
{
/*
* Primary USB is used only for DP functionality on cheza platform.
* Hence Setting up only Secondary USB DWC3 controller.
*/
setup_usb_host1(&usb1_board_data);
gpio_output(GPIO(120), 1); /* Deassert HUB_RST_L to enable hub. */
}

View File

@@ -14,7 +14,22 @@
*/
#include <arch/stages.h>
#include <soc/usb.h>
#include <soc/qclib_common.h>
static void prepare_usb(void)
{
/*
* Do DWC3 core and phy reset. Kick these resets
* off early so they get at least 1ms to settle.
*/
reset_usb1();
}
void platform_romstage_main(void)
{
prepare_usb();
/* QCLib: DDR init & train */
qclib_load_and_run();
}

View File

@@ -16,6 +16,7 @@ config BOARD_GOOGLE_BASEBOARD_CYAN
select HAVE_ACPI_RESUME
select PCIEXP_L1_SUB_STATE if !BOARD_GOOGLE_CYAN
select SYSTEM_TYPE_LAPTOP
select USE_GOOGLE_FSP
if BOARD_GOOGLE_BASEBOARD_CYAN

View File

@@ -35,7 +35,7 @@ Scope (\_SB.PCI0.I2C2)
}
})
Method(_CRS, 0x0, NotSerialized)
Method(_CRS, 0x0, Serialized)
{
Name(SBUF,ResourceTemplate ()
{

View File

@@ -26,7 +26,7 @@ Scope (\_SB.PCI0.I2C5)
Name (_DDN, AUDIO_CODEC_DDN)
Name (_UID, 1)
Method(_CRS, 0x0, NotSerialized)
Method(_CRS, 0x0, Serialized)
{
Name(SBUF,ResourceTemplate ()
{

View File

@@ -16,15 +16,12 @@
#include <soc/romstage.h>
#include <baseboard/variants.h>
#include <chip.h>
#include "spd/spd_util.h"
/* All FSP specific code goes in this block */
void mainboard_romstage_entry(struct romstage_params *rp)
{
struct pei_data *ps = rp->pei_data;
mainboard_fill_spd_data(ps);
/* Call back into chipset code with platform values updated. */
romstage_common(rp);
}
@@ -32,16 +29,7 @@ void mainboard_romstage_entry(struct romstage_params *rp)
void mainboard_memory_init_params(struct romstage_params *params,
MEMORY_INIT_UPD *memory_params)
{
/* Update SPD data */
if (CONFIG(BOARD_GOOGLE_CYAN)) {
memory_params->PcdMemoryTypeEnable = MEM_DDR3;
memory_params->PcdMemorySpdPtr =
(u32)params->pei_data->spd_data_ch0;
} else
memory_params->PcdMemoryTypeEnable = MEM_LPDDR3;
memory_params->PcdMemChannel0Config = params->pei_data->spd_ch0_config;
memory_params->PcdMemChannel1Config = params->pei_data->spd_ch1_config;
spd_memory_init_params(memory_params);
/* Variant-specific memory params */
variant_memory_init_params(memory_params);

View File

@@ -40,11 +40,24 @@ __weak uint8_t get_ramid(void)
return gpio_base2_value(spd_gpios, ARRAY_SIZE(spd_gpios));
}
static void *get_spd_pointer(char *spd_file_content, int total_spds, int *dual)
static void *get_spd_pointer(int *dual)
{
char *spd_file;
size_t spd_file_len;
int total_spds;
int ram_id = 0;
int spd_index = 0;
/* Find the SPD data in CBFS. */
spd_file = cbfs_boot_map_with_leak("spd.bin", CBFS_TYPE_SPD,
&spd_file_len);
if (!spd_file)
die("SPD data not found.");
if (spd_file_len < SPD_PAGE_LEN)
die("Missing SPD data.");
total_spds = spd_file_len / SPD_PAGE_LEN;
ram_id = get_ramid();
printk(BIOS_DEBUG, "ram_id=%d, total_spds: %d\n", ram_id, total_spds);
@@ -54,33 +67,20 @@ static void *get_spd_pointer(char *spd_file_content, int total_spds, int *dual)
return NULL;
}
/* Return the serial product data for the RAM */
return &spd_file_content[SPD_PAGE_LEN * spd_index];
return &spd_file[SPD_PAGE_LEN * spd_index];
}
/* Copy SPD data for on-board memory */
void mainboard_fill_spd_data(struct pei_data *ps)
void spd_memory_init_params(MEMORY_INIT_UPD *memory_params)
{
char *spd_file;
size_t spd_file_len;
void *spd_content;
int dual_channel = 0;
/* Find the SPD data in CBFS. */
spd_file = cbfs_boot_map_with_leak("spd.bin", CBFS_TYPE_SPD,
&spd_file_len);
if (!spd_file)
die("SPD data not found.");
if (spd_file_len < SPD_PAGE_LEN)
die("Missing SPD data.");
/*
* Both channels are always present in SPD data. Always use matched
* DIMMs so use the same SPD data for each DIMM.
*/
spd_content = get_spd_pointer(spd_file,
spd_file_len / SPD_PAGE_LEN,
&dual_channel);
spd_content = get_spd_pointer(&dual_channel);
if (CONFIG(DISPLAY_SPD_DATA) && spd_content != NULL) {
printk(BIOS_DEBUG, "SPD Data:\n");
hexdump(spd_content, SPD_PAGE_LEN);
@@ -94,21 +94,27 @@ void mainboard_fill_spd_data(struct pei_data *ps)
* 2=DimmDisabled
*/
if (spd_content != NULL) {
ps->spd_data_ch0 = spd_content;
ps->spd_ch0_config = 1;
memory_params->PcdMemChannel0Config = 1;
printk(BIOS_DEBUG, "Channel 0 DIMM soldered down\n");
if (dual_channel) {
printk(BIOS_DEBUG, "Channel 1 DIMM soldered down\n");
ps->spd_data_ch1 = spd_content;
ps->spd_ch1_config = 1;
memory_params->PcdMemChannel1Config = 1;
} else {
printk(BIOS_DEBUG, "Channel 1 DIMM not installed\n");
ps->spd_ch1_config = 2;
memory_params->PcdMemChannel1Config = 2;
}
}
/* Update SPD data */
if (CONFIG(BOARD_GOOGLE_CYAN)) {
memory_params->PcdMemoryTypeEnable = MEM_DDR3;
memory_params->PcdMemorySpdPtr = (uintptr_t)spd_content;
} else {
memory_params->PcdMemoryTypeEnable = MEM_LPDDR3;
}
}
static void set_dimm_info(uint8_t *spd, struct dimm_info *dimm)
static void set_dimm_info(const uint8_t *spd, struct dimm_info *dimm)
{
const int spd_capmb[8] = { 1, 2, 4, 8, 16, 32, 64, 0 };
const int spd_ranks[8] = { 1, 2, 3, 4, -1, -1, -1, -1 };
@@ -171,9 +177,15 @@ static void set_dimm_info(uint8_t *spd, struct dimm_info *dimm)
void mainboard_save_dimm_info(struct romstage_params *params)
{
const void *spd_content;
int dual_channel;
struct dimm_info *dimm;
struct memory_info *mem_info;
spd_content = get_spd_pointer(&dual_channel);
if (spd_content == NULL)
return;
/*
* Allocate CBMEM area for DIMM information used to populate SMBIOS
* table 17
@@ -186,13 +198,13 @@ void mainboard_save_dimm_info(struct romstage_params *params)
/* Describe the first channel memory */
dimm = &mem_info->dimm[0];
set_dimm_info(params->pei_data->spd_data_ch0, dimm);
set_dimm_info(spd_content, dimm);
mem_info->dimm_cnt = 1;
/* Describe the second channel memory */
if (params->pei_data->spd_ch1_config == 1) {
if (dual_channel) {
dimm = &mem_info->dimm[1];
set_dimm_info(params->pei_data->spd_data_ch1, dimm);
set_dimm_info(spd_content, dimm);
dimm->channel_num = 1;
mem_info->dimm_cnt = 2;
}

View File

@@ -16,7 +16,10 @@
#ifndef SPD_UTIL_H
#define SPD_UTIL_H
#include <fsp/soc_binding.h>
uint8_t get_ramid(void);
int get_variant_spd_index(int ram_id, int *dual);
void spd_memory_init_params(MEMORY_INIT_UPD *memory_params);
#endif /* SPD_UTIL_H */

View File

@@ -73,12 +73,6 @@ chip soc/intel/braswell
register "ISPEnable" = "0" # Disable IUNIT
register "ISPPciDevConfig" = "3"
register "PcdSdDetectChk" = "0" # Disable SD card detect
# Follow Intel recommendation to set BSW D-stepping PERPORTRXISET 2 (low strength)
register "D0Usb2Port0PerPortRXISet" = "2"
register "D0Usb2Port1PerPortRXISet" = "2"
register "D0Usb2Port2PerPortRXISet" = "2"
register "D0Usb2Port3PerPortRXISet" = "2"
register "D0Usb2Port4PerPortRXISet" = "2"
# LPE audio codec settings
register "lpe_codec_clk_src" = "LPE_CLK_SRC_XTAL" # 19.2MHz clock

View File

@@ -19,29 +19,36 @@ void board_silicon_USB2_override(SILICON_INIT_UPD *params)
{
if (SocStepping() >= SocD0) {
//Follow Intel recommendation to set
//BSW D-stepping PERPORTRXISET 2 (low strength)
params->Usb2Port0PerPortPeTxiSet = 7;
params->Usb2Port0PerPortTxiSet = 0;
params->Usb2Port0IUsbTxEmphasisEn = 3;
params->Usb2Port0PerPortTxPeHalf = 1;
params->D0Usb2Port0PerPortRXISet = 2;
params->Usb2Port1PerPortPeTxiSet = 7;
params->Usb2Port1PerPortTxiSet = 0;
params->Usb2Port1IUsbTxEmphasisEn = 3;
params->Usb2Port1PerPortTxPeHalf = 1;
params->D0Usb2Port1PerPortRXISet = 2;
params->Usb2Port2PerPortPeTxiSet = 7;
params->Usb2Port2PerPortTxiSet = 6;
params->Usb2Port2IUsbTxEmphasisEn = 3;
params->Usb2Port2PerPortTxPeHalf = 1;
params->D0Usb2Port2PerPortRXISet = 2;
params->Usb2Port3PerPortPeTxiSet = 7;
params->Usb2Port3PerPortTxiSet = 6;
params->Usb2Port3IUsbTxEmphasisEn = 3;
params->Usb2Port3PerPortTxPeHalf = 1;
params->D0Usb2Port3PerPortRXISet = 2;
params->Usb2Port4PerPortPeTxiSet = 7;
params->Usb2Port4PerPortTxiSet = 6;
params->Usb2Port4IUsbTxEmphasisEn = 3;
params->Usb2Port4PerPortTxPeHalf = 1;
params->D0Usb2Port4PerPortRXISet = 2;
}
}

View File

@@ -18,6 +18,7 @@ romstage-y += romstage.c
romstage-y += spd_util.c
ramstage-y += gpio.c
ramstage-y += ramstage.c
SPD_BIN = $(obj)/spd.bin

View File

@@ -80,13 +80,6 @@ chip soc/intel/braswell
register "I2C5Frequency" = "1"
register "I2C6Frequency" = "1"
# Follow Intel recommendation to set BSW D-stepping PERPORTRXISET 2 (low strength)
register "D0Usb2Port0PerPortRXISet" = "2"
register "D0Usb2Port1PerPortRXISet" = "2"
register "D0Usb2Port2PerPortRXISet" = "2"
register "D0Usb2Port3PerPortRXISet" = "2"
register "D0Usb2Port4PerPortRXISet" = "2"
# LPE audio codec settings
register "lpe_codec_clk_src" = "LPE_CLK_SRC_XTAL" # 19.2MHz clock

View File

@@ -1,8 +1,7 @@
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2014 Google Inc.
* Copyright (C) 2015 Intel Corporation.
* Copyright (C) 2014 Intel Corporation
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -14,14 +13,18 @@
* GNU General Public License for more details.
*/
#ifndef _SOC_PEI_WRAPPER_H_
#define _SOC_PEI_WRAPPER_H_
#include <soc/ramstage.h>
#include <soc/pei_data.h>
void board_silicon_USB2_override(SILICON_INIT_UPD *params)
{
if (SocStepping() >= SocD0) {
typedef int ABI_X86(*pei_wrapper_entry_t)(struct pei_data *pei_data);
void soc_fill_pei_data(struct pei_data *pei_data);
void mainboard_fill_pei_data(struct pei_data *pei_data);
#endif
//Follow Intel recommendation to set
//BSW D-stepping PERPORTRXISET 2 (low strength)
params->D0Usb2Port0PerPortRXISet = 2;
params->D0Usb2Port1PerPortRXISet = 2;
params->D0Usb2Port2PerPortRXISet = 2;
params->D0Usb2Port3PerPortRXISet = 2;
params->D0Usb2Port4PerPortRXISet = 2;
}
}

View File

@@ -80,13 +80,6 @@ chip soc/intel/braswell
register "I2C5Frequency" = "1"
register "I2C6Frequency" = "1"
# Follow Intel recommendation to set BSW D-stepping PERPORTRXISET 2 (low strength)
register "D0Usb2Port0PerPortRXISet" = "2"
register "D0Usb2Port1PerPortRXISet" = "2"
register "D0Usb2Port2PerPortRXISet" = "2"
register "D0Usb2Port3PerPortRXISet" = "2"
register "D0Usb2Port4PerPortRXISet" = "2"
# LPE audio codec settings
register "lpe_codec_clk_src" = "LPE_CLK_SRC_XTAL" # 19.2MHz clock

View File

@@ -36,5 +36,13 @@ void board_silicon_USB2_override(SILICON_INIT_UPD *params)
params->Usb2Port3PerPortTxiSet = 0;
params->Usb2Port3IUsbTxEmphasisEn = 2;
params->Usb2Port3PerPortTxPeHalf = 1;
//Follow Intel recommendation to set
//BSW D-stepping PERPORTRXISET 2 (low strength)
params->D0Usb2Port0PerPortRXISet = 2;
params->D0Usb2Port1PerPortRXISet = 2;
params->D0Usb2Port2PerPortRXISet = 2;
params->D0Usb2Port3PerPortRXISet = 2;
params->D0Usb2Port4PerPortRXISet = 2;
}
}

View File

@@ -19,7 +19,6 @@
#include <console/console.h>
#include <gpio.h>
#include <soc/gpio.h>
#include <soc/pei_data.h>
#include <soc/romstage.h>
#include <string.h>

View File

@@ -34,10 +34,6 @@ struct max77620_init_reg {
u8 delay;
};
static struct max77620_init_reg init_list[] = {
/* TODO */
};
static void pmic_write_reg(unsigned bus, uint8_t reg, uint8_t val, int delay)
{
if (i2c_writeb(bus, MAX77620_I2C_ADDR, reg, val)) {
@@ -51,20 +47,8 @@ static void pmic_write_reg(unsigned bus, uint8_t reg, uint8_t val, int delay)
}
}
static void pmic_slam_defaults(unsigned bus)
{
int i;
for (i = 0; i < ARRAY_SIZE(init_list); i++) {
struct max77620_init_reg *reg = &init_list[i];
pmic_write_reg(bus, reg->reg, reg->val, reg->delay);
}
}
void pmic_init(unsigned bus)
{
/* Restore PMIC POR defaults, in case kernel changed 'em */
pmic_slam_defaults(bus);
/* Setup/Enable GPIO5 - VDD_CPU_REG_EN */
pmic_write_reg(bus, MAX77620_GPIO5_REG, 0x09, 1);

View File

@@ -15,16 +15,16 @@
* GNU General Public License for more details.
*/
#include <string.h>
#include <baseboard/variant.h>
#include <ec/google/chromeec/ec.h>
#include <gpio.h>
#include <soc/pei_data.h>
#include <soc/pei_wrapper.h>
#include <soc/romstage.h>
#include "spd/spd.h"
#include <variant/ec.h>
#include <variant/gpio.h>
#include "spd/spd_util.h"
#include "spd/spd.h"
void mainboard_romstage_entry(struct romstage_params *params)
{
#ifdef EC_ENABLE_KEYBOARD_BACKLIGHT
@@ -32,18 +32,6 @@ void mainboard_romstage_entry(struct romstage_params *params)
if (params->power_state->prev_sleep_state != ACPI_S3)
google_chromeec_kbbacklight(25);
#endif
/* Get SPD index */
gpio_t spd_gpios[] = {
GPIO_MEM_CONFIG_0,
GPIO_MEM_CONFIG_1,
GPIO_MEM_CONFIG_2,
GPIO_MEM_CONFIG_3,
};
params->pei_data->mem_cfg_id =
gpio_base2_value(spd_gpios, ARRAY_SIZE(spd_gpios));
/* Fill out PEI DATA */
mainboard_fill_pei_data(params->pei_data);
mainboard_fill_spd_data(params->pei_data);
/* Initialize memory */
romstage_common(params);
}
@@ -51,26 +39,18 @@ void mainboard_romstage_entry(struct romstage_params *params)
void mainboard_memory_init_params(struct romstage_params *params,
MEMORY_INIT_UPD *memory_params)
{
if (params->pei_data->spd_data[0][0][0] != 0) {
memory_params->MemorySpdPtr00 =
(UINT32)(params->pei_data->spd_data[0][0]);
memory_params->MemorySpdPtr10 =
(UINT32)(params->pei_data->spd_data[1][0]);
}
memcpy(memory_params->DqByteMapCh0, params->pei_data->dq_map[0],
sizeof(params->pei_data->dq_map[0]));
memcpy(memory_params->DqByteMapCh1, params->pei_data->dq_map[1],
sizeof(params->pei_data->dq_map[1]));
memcpy(memory_params->DqsMapCpu2DramCh0, params->pei_data->dqs_map[0],
sizeof(params->pei_data->dqs_map[0]));
memcpy(memory_params->DqsMapCpu2DramCh1, params->pei_data->dqs_map[1],
sizeof(params->pei_data->dqs_map[1]));
memcpy(memory_params->RcompResistor, params->pei_data->RcompResistor,
sizeof(params->pei_data->RcompResistor));
memcpy(memory_params->RcompTarget, params->pei_data->RcompTarget,
sizeof(params->pei_data->RcompTarget));
/* Get SPD index */
const gpio_t spd_gpios[] = {
GPIO_MEM_CONFIG_0,
GPIO_MEM_CONFIG_1,
GPIO_MEM_CONFIG_2,
GPIO_MEM_CONFIG_3,
};
const int spd_idx = gpio_base2_value(spd_gpios, ARRAY_SIZE(spd_gpios));
memory_params->MemorySpdDataLen = SPD_LEN;
memory_params->DqPinsInterleaved = FALSE;
if (CONFIG(BOARD_GOOGLE_CAROLINE))
memory_params->DdrFreqLimit = 1600;
spd_memory_init_params(memory_params, spd_idx);
variant_memory_init_params(memory_params, spd_idx);
}

View File

@@ -19,10 +19,11 @@
#include <console/console.h>
#include <gpio.h>
#include <soc/gpio.h>
#include <soc/pei_data.h>
#include <soc/romstage.h>
#include <string.h>
#include <baseboard/variant.h>
#include "spd_util.h"
#include "spd.h"
static void mainboard_print_spd_info(uint8_t spd[])
@@ -83,13 +84,11 @@ __weak int is_dual_channel(const int spd_index)
}
/* Copy SPD data for on-board memory */
void mainboard_fill_spd_data(struct pei_data *pei_data)
void spd_memory_init_params(MEMORY_INIT_UPD *const memory_params, int spd_index)
{
char *spd_file;
uint8_t *spd_file;
size_t spd_file_len;
int spd_index;
spd_index = pei_data->mem_cfg_id;
printk(BIOS_INFO, "SPD index %d\n", spd_index);
/* Load SPD data from CBFS */
@@ -108,15 +107,15 @@ void mainboard_fill_spd_data(struct pei_data *pei_data)
spd_index = 1;
}
/* Assume same memory in both channels */
spd_index *= SPD_LEN;
memcpy(pei_data->spd_data[0][0], spd_file + spd_index, SPD_LEN);
if (is_dual_channel(spd_index))
memcpy(pei_data->spd_data[1][0], spd_file + spd_index, SPD_LEN);
const size_t spd_offset = spd_index * SPD_LEN;
/* Make sure a valid SPD was found */
if (pei_data->spd_data[0][0][0] == 0)
if (spd_file[spd_offset] == 0)
die("Invalid SPD data.");
mainboard_print_spd_info(pei_data->spd_data[0][0]);
/* Assume same memory in both channels */
memory_params->MemorySpdPtr00 = (uintptr_t)spd_file + spd_offset;
if (is_dual_channel(spd_index))
memory_params->MemorySpdPtr10 = memory_params->MemorySpdPtr00;
mainboard_print_spd_info(spd_file + spd_offset);
}

View File

@@ -1,8 +1,6 @@
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2014 Google Inc.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; version 2 of the License.
@@ -13,14 +11,11 @@
* GNU General Public License for more details.
*/
#ifndef _SOC_PEI_WRAPPER_H_
#define _SOC_PEI_WRAPPER_H_
#ifndef SPD_UTIL_H
#define SPD_UTIL_H
#include <soc/pei_data.h>
#include <fsp/soc_binding.h>
typedef int ABI_X86(*pei_wrapper_entry_t)(struct pei_data *pei_data);
void spd_memory_init_params(MEMORY_INIT_UPD *, int spd_index);
void broadwell_fill_pei_data(struct pei_data *pei_data);
void mainboard_fill_pei_data(struct pei_data *pei_data);
#endif
#endif /* SPD_UTIL_H */

View File

@@ -17,10 +17,10 @@
#include <stdint.h>
#include <string.h>
#include <baseboard/variant.h>
#include <soc/pei_data.h>
#include <soc/pei_wrapper.h>
#include <fsp/soc_binding.h>
void mainboard_fill_pei_data(struct pei_data *pei_data)
void variant_memory_init_params(
MEMORY_INIT_UPD *const memory_params, const int spd_index)
{
/* DQ byte map */
const u8 dq_map[2][12] = {
@@ -39,12 +39,14 @@ void mainboard_fill_pei_data(struct pei_data *pei_data)
/* Rcomp target */
const u16 RcompTarget[5] = { 100, 40, 40, 23, 40 };
memcpy(pei_data->dq_map, dq_map, sizeof(dq_map));
memcpy(pei_data->dqs_map, dqs_map, sizeof(dqs_map));
memcpy(pei_data->RcompResistor, RcompResistor,
sizeof(RcompResistor));
memcpy(pei_data->RcompTarget, RcompTarget,
sizeof(RcompTarget));
memcpy(memory_params->DqByteMapCh0, dq_map,
sizeof(memory_params->DqByteMapCh0) * 2);
memcpy(memory_params->DqsMapCpu2DramCh0, dqs_map,
sizeof(memory_params->DqsMapCpu2DramCh0) * 2);
memcpy(memory_params->RcompResistor, RcompResistor,
sizeof(memory_params->RcompResistor));
memcpy(memory_params->RcompTarget, RcompTarget,
sizeof(memory_params->RcompTarget));
}
int is_dual_channel(const int spd_index)

View File

@@ -15,7 +15,10 @@
#ifndef GLADOS_VARIANT_H
#define GLADOS_VARIANT_H
#include <fsp/soc_binding.h>
int is_dual_channel(const int spd_index);
void mainboard_gpio_smi_sleep(void);
void variant_memory_init_params(MEMORY_INIT_UPD *memory_params, int spd_index);
#endif /* GLADOS_VARIANT_H */

View File

@@ -15,14 +15,14 @@
*/
#include <baseboard/variant.h>
#include <fsp/soc_binding.h>
#include <gpio.h>
#include <stdint.h>
#include <string.h>
#include <soc/pei_data.h>
#include <soc/pei_wrapper.h>
#include <variant/gpio.h>
void mainboard_fill_pei_data(struct pei_data *pei_data)
void variant_memory_init_params(
MEMORY_INIT_UPD *const memory_params, const int spd_index)
{
/* DQ byte map */
const u8 dq_map[2][12] = {
@@ -41,12 +41,15 @@ void mainboard_fill_pei_data(struct pei_data *pei_data)
/* Rcomp target */
const u16 RcompTarget[5] = { 100, 40, 40, 23, 40 };
memcpy(pei_data->dq_map, dq_map, sizeof(dq_map));
memcpy(pei_data->dqs_map, dqs_map, sizeof(dqs_map));
memcpy(pei_data->RcompResistor, RcompResistor,
sizeof(RcompResistor));
memcpy(pei_data->RcompTarget, RcompTarget,
sizeof(RcompTarget));
memcpy(memory_params->DqByteMapCh0, dq_map,
sizeof(memory_params->DqByteMapCh0) * 2);
memcpy(memory_params->DqsMapCpu2DramCh0, dqs_map,
sizeof(memory_params->DqsMapCpu2DramCh0) * 2);
memcpy(memory_params->RcompResistor, RcompResistor,
sizeof(memory_params->RcompResistor));
memcpy(memory_params->RcompTarget, RcompTarget,
sizeof(memory_params->RcompTarget));
memory_params->DdrFreqLimit = 1600;
}
void mainboard_gpio_smi_sleep(void)

View File

@@ -15,14 +15,14 @@
*/
#include <baseboard/variant.h>
#include <fsp/soc_binding.h>
#include <gpio.h>
#include <stdint.h>
#include <string.h>
#include <soc/pei_data.h>
#include <soc/pei_wrapper.h>
#include <variant/gpio.h>
void mainboard_fill_pei_data(struct pei_data *pei_data)
void variant_memory_init_params(
MEMORY_INIT_UPD *const memory_params, const int spd_index)
{
/* DQ byte map */
const u8 dq_map[2][12] = {
@@ -41,12 +41,14 @@ void mainboard_fill_pei_data(struct pei_data *pei_data)
/* Rcomp target */
const u16 RcompTarget[5] = { 100, 40, 40, 23, 40 };
memcpy(pei_data->dq_map, dq_map, sizeof(dq_map));
memcpy(pei_data->dqs_map, dqs_map, sizeof(dqs_map));
memcpy(pei_data->RcompResistor, RcompResistor,
sizeof(RcompResistor));
memcpy(pei_data->RcompTarget, RcompTarget,
sizeof(RcompTarget));
memcpy(memory_params->DqByteMapCh0, dq_map,
sizeof(memory_params->DqByteMapCh0) * 2);
memcpy(memory_params->DqsMapCpu2DramCh0, dqs_map,
sizeof(memory_params->DqsMapCpu2DramCh0) * 2);
memcpy(memory_params->RcompResistor, RcompResistor,
sizeof(memory_params->RcompResistor));
memcpy(memory_params->RcompTarget, RcompTarget,
sizeof(memory_params->RcompTarget));
}
void mainboard_gpio_smi_sleep(void)

View File

@@ -15,14 +15,14 @@
*/
#include <baseboard/variant.h>
#include <fsp/soc_binding.h>
#include <gpio.h>
#include <stdint.h>
#include <string.h>
#include <soc/pei_data.h>
#include <soc/pei_wrapper.h>
#include <variant/gpio.h>
void mainboard_fill_pei_data(struct pei_data *pei_data)
void variant_memory_init_params(
MEMORY_INIT_UPD *const memory_params, const int spd_index)
{
/* DQ byte map */
const u8 dq_map[2][12] = {
@@ -41,12 +41,14 @@ void mainboard_fill_pei_data(struct pei_data *pei_data)
/* Rcomp target */
const u16 RcompTarget[5] = { 100, 40, 40, 23, 40 };
memcpy(pei_data->dq_map, dq_map, sizeof(dq_map));
memcpy(pei_data->dqs_map, dqs_map, sizeof(dqs_map));
memcpy(pei_data->RcompResistor, RcompResistor,
sizeof(RcompResistor));
memcpy(pei_data->RcompTarget, RcompTarget,
sizeof(RcompTarget));
memcpy(memory_params->DqByteMapCh0, dq_map,
sizeof(memory_params->DqByteMapCh0) * 2);
memcpy(memory_params->DqsMapCpu2DramCh0, dqs_map,
sizeof(memory_params->DqsMapCpu2DramCh0) * 2);
memcpy(memory_params->RcompResistor, RcompResistor,
sizeof(memory_params->RcompResistor));
memcpy(memory_params->RcompTarget, RcompTarget,
sizeof(memory_params->RcompTarget));
}
void mainboard_gpio_smi_sleep(void)

View File

@@ -15,14 +15,14 @@
*/
#include <baseboard/variant.h>
#include <fsp/soc_binding.h>
#include <gpio.h>
#include <stdint.h>
#include <string.h>
#include <soc/pei_data.h>
#include <soc/pei_wrapper.h>
#include <variant/gpio.h>
void mainboard_fill_pei_data(struct pei_data *pei_data)
void variant_memory_init_params(
MEMORY_INIT_UPD *const memory_params, const int spd_index)
{
/* DQ byte map */
const u8 dq_map[2][12] = {
@@ -41,12 +41,14 @@ void mainboard_fill_pei_data(struct pei_data *pei_data)
/* Rcomp target */
const u16 RcompTarget[5] = { 100, 40, 40, 23, 40 };
memcpy(pei_data->dq_map, dq_map, sizeof(dq_map));
memcpy(pei_data->dqs_map, dqs_map, sizeof(dqs_map));
memcpy(pei_data->RcompResistor, RcompResistor,
sizeof(RcompResistor));
memcpy(pei_data->RcompTarget, RcompTarget,
sizeof(RcompTarget));
memcpy(memory_params->DqByteMapCh0, dq_map,
sizeof(memory_params->DqByteMapCh0) * 2);
memcpy(memory_params->DqsMapCpu2DramCh0, dqs_map,
sizeof(memory_params->DqsMapCpu2DramCh0) * 2);
memcpy(memory_params->RcompResistor, RcompResistor,
sizeof(memory_params->RcompResistor));
memcpy(memory_params->RcompTarget, RcompTarget,
sizeof(memory_params->RcompTarget));
}
void mainboard_gpio_smi_sleep(void)

View File

@@ -17,8 +17,7 @@
#include <stdint.h>
#include <string.h>
#include <baseboard/variant.h>
#include <soc/pei_data.h>
#include <soc/pei_wrapper.h>
#include <fsp/soc_binding.h>
#define K4E6E304EB_MEM_ID 0x5
@@ -29,7 +28,8 @@
#define MEM_SINGLE_CHANB 0xb
#define MEM_SINGLE_CHANC 0xc
void mainboard_fill_pei_data(struct pei_data *pei_data)
void variant_memory_init_params(
MEMORY_INIT_UPD *const params, const int spd_index)
{
/* DQ byte map */
const u8 dq_map[2][12] = {
@@ -54,17 +54,18 @@ void mainboard_fill_pei_data(struct pei_data *pei_data)
/* Default Rcomp Target assignment */
const u16 *targeted_rcomp = RcompTarget;
memcpy(pei_data->dq_map, dq_map, sizeof(dq_map));
memcpy(pei_data->dqs_map, dqs_map, sizeof(dqs_map));
memcpy(pei_data->RcompResistor, RcompResistor,
sizeof(RcompResistor));
/* Override Rcomp Target assignment for specific SKU(s) */
if (pei_data->mem_cfg_id == K4E6E304EB_MEM_ID)
if (spd_index == K4E6E304EB_MEM_ID)
targeted_rcomp = StrengthendRcompTarget;
memcpy(pei_data->RcompTarget, targeted_rcomp,
sizeof(pei_data->RcompTarget));
memcpy(params->DqByteMapCh0, dq_map,
sizeof(params->DqByteMapCh0) * 2);
memcpy(params->DqsMapCpu2DramCh0, dqs_map,
sizeof(params->DqsMapCpu2DramCh0) * 2);
memcpy(params->RcompResistor, RcompResistor,
sizeof(params->RcompResistor));
memcpy(params->RcompTarget, targeted_rcomp,
sizeof(params->RcompTarget));
}
int is_dual_channel(const int spd_index)

View File

@@ -17,12 +17,12 @@
#include <stdint.h>
#include <string.h>
#include <baseboard/variant.h>
#include <soc/pei_data.h>
#include <soc/pei_wrapper.h>
#include <fsp/soc_binding.h>
#define K4E6E304EE_MEM_ID 0x3
void mainboard_fill_pei_data(struct pei_data *pei_data)
void variant_memory_init_params(
MEMORY_INIT_UPD *const memory_params, const int spd_index)
{
/* DQ byte map */
const u8 dq_map[2][12] = {
@@ -47,15 +47,16 @@ void mainboard_fill_pei_data(struct pei_data *pei_data)
/* Default Rcomp Target assignment */
const u16 *targeted_rcomp = RcompTarget;
memcpy(pei_data->dq_map, dq_map, sizeof(dq_map));
memcpy(pei_data->dqs_map, dqs_map, sizeof(dqs_map));
memcpy(pei_data->RcompResistor, RcompResistor,
sizeof(RcompResistor));
/* Override Rcomp Target assignment for specific SKU(s) */
if (pei_data->mem_cfg_id == K4E6E304EE_MEM_ID)
if (spd_index == K4E6E304EE_MEM_ID)
targeted_rcomp = StrengthendRcompTarget;
memcpy(pei_data->RcompTarget, targeted_rcomp,
sizeof(pei_data->RcompTarget));
memcpy(memory_params->DqByteMapCh0, dq_map,
sizeof(memory_params->DqByteMapCh0) * 2);
memcpy(memory_params->DqsMapCpu2DramCh0, dqs_map,
sizeof(memory_params->DqsMapCpu2DramCh0) * 2);
memcpy(memory_params->RcompResistor, RcompResistor,
sizeof(memory_params->RcompResistor));
memcpy(memory_params->RcompTarget, targeted_rcomp,
sizeof(memory_params->RcompTarget));
}

View File

@@ -64,7 +64,7 @@ config GBB_HWID
depends on CHROMEOS
default "HATCH TEST 1823" if BOARD_GOOGLE_HATCH
default "HATCH_WHL TEST 2374" if BOARD_GOOGLE_HATCH_WHL
default "KOHAKU TEST 1953" if BOARD_GOOGLE_HATCH_WHL
default "KOHAKU TEST 1953" if BOARD_GOOGLE_KOHAKU
config MAINBOARD_DIR
string

View File

@@ -30,8 +30,8 @@ static const struct pad_config gpio_table[] = {
PAD_CFG_GPI_INT(GPP_A6, NONE, PLTRST, LEVEL),
/* A7 : PP3300_SOC_A */
PAD_NC(GPP_A7, NONE),
/* A8 : EMR_GARAGE_DET */
PAD_CFG_GPI_GPIO_DRIVER(GPP_A8, NONE, DEEP),
/* A8 : PEN_GARAGE_DET_L */
PAD_CFG_GPI_GPIO_DRIVER_SCI(GPP_A8, NONE, DEEP, LEVEL, NONE),
/* A9 : ESPI_CLK */
/* A10 : FPMCU_PCH_BOOT1 */
PAD_CFG_GPO(GPP_A10, 0, DEEP),

View File

@@ -78,15 +78,17 @@ chip soc/intel/cannonlake
register "generic.probed" = "1"
register "generic.reset_gpio" =
"ACPI_GPIO_OUTPUT_ACTIVE_LOW(GPP_D15)"
register "generic.reset_delay_ms" = "30"
register "generic.reset_off_delay_ms" = "3"
register "generic.reset_delay_ms" = "10"
register "generic.reset_off_delay_ms" = "1"
register "generic.has_power_resource" = "1"
register "hid_desc_reg_offset" = "0x01"
device i2c 5d on end
end
chip drivers/generic/gpio_keys
register "name" = ""PENH""
register "gpio" = "ACPI_GPIO_INPUT_ACTIVE_HIGH(GPP_A8)"
register "gpio" = "ACPI_GPIO_IRQ_EDGE_BOTH(GPP_A8)"
register "key.wake" = "GPE0_DW0_08"
register "key.wakeup_event_action" = "EV_ACT_ASSERTED"
register "key.dev_name" = ""EJCT""
register "key.linux_code" = "SW_PEN_INSERTED"
register "key.linux_input_type" = "EV_SW"

View File

@@ -63,15 +63,17 @@ chip soc/intel/cannonlake
register "generic.probed" = "1"
register "generic.reset_gpio" =
"ACPI_GPIO_OUTPUT_ACTIVE_LOW(GPP_D15)"
register "generic.reset_delay_ms" = "30"
register "generic.reset_off_delay_ms" = "3"
register "generic.reset_delay_ms" = "10"
register "generic.reset_off_delay_ms" = "1"
register "generic.has_power_resource" = "1"
register "hid_desc_reg_offset" = "0x01"
device i2c 5d on end
end
chip drivers/generic/gpio_keys
register "name" = ""PENH""
register "gpio" = "ACPI_GPIO_INPUT_ACTIVE_HIGH(GPP_A8)"
register "gpio" = "ACPI_GPIO_IRQ_EDGE_BOTH(GPP_A8)"
register "key.wake" = "GPE0_DW0_08"
register "key.wakeup_event_action" = "EV_ACT_ASSERTED"
register "key.dev_name" = ""EJCT""
register "key.linux_code" = "SW_PEN_INSERTED"
register "key.linux_input_type" = "EV_SW"

View File

@@ -145,13 +145,13 @@ static void mainboard_init(void *chip_info)
pm_write8(PM_PCIB_CFG, pm_read8(PM_PCIB_CFG) | PM_GENINT_DISABLE);
/* Set low-power mode for BayHub eMMC bridge's PCIe clock. */
clrsetbits_le32((uint32_t *)(MISC_MMIO_BASE + GPP_CLK_CNTRL),
clrsetbits_le32((uint32_t *)(ACPIMMIO_MISC_BASE + GPP_CLK_CNTRL),
GPP_CLK2_REQ_MAP_MASK,
GPP_CLK2_REQ_MAP_CLK_REQ2 <<
GPP_CLK2_REQ_MAP_SHIFT);
/* Same for the WiFi */
clrsetbits_le32((uint32_t *)(MISC_MMIO_BASE + GPP_CLK_CNTRL),
clrsetbits_le32((uint32_t *)(ACPIMMIO_MISC_BASE + GPP_CLK_CNTRL),
GPP_CLK0_REQ_MAP_MASK,
GPP_CLK0_REQ_MAP_CLK_REQ0 <<
GPP_CLK0_REQ_MAP_SHIFT);

View File

@@ -35,7 +35,7 @@ Device (I2S)
Name (RBUF, ResourceTemplate () {
// Memory resource is for MISC FCH register set.
// It is needed for enabling the clock.
Memory32Fixed(ReadWrite, MISC_MMIO_BASE, 0x100)
Memory32Fixed(ReadWrite, ACPIMMIO_MISC_BASE, 0x100)
})
Return (RBUF)

View File

@@ -6,7 +6,7 @@
16 36 0B 35 00 00 16 36 0B 35 16 36 0B 35 00 00
00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
00 00 00 00 00 00 9C B5 00 00 00 00 E7 00 60 5B
00 00 00 00 00 00 9C B5 00 00 00 00 E7 00 30 53
0F 01 02 00 00 00 00 00 00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00

View File

@@ -27,6 +27,7 @@ void setup_chromeos_gpios(void)
gpio_input_pullup(EC_IRQ);
gpio_input_pullup(CR50_IRQ);
gpio_output(GPIO_RESET, 0);
gpio_output(GPIO_EN_SPK_AMP, 0);
}
void fill_lb_gpios(struct lb_gpios *gpios)
@@ -38,6 +39,7 @@ void fill_lb_gpios(struct lb_gpios *gpios)
{EC_IN_RW.id, ACTIVE_HIGH, -1, "EC in RW"},
{EC_IRQ.id, ACTIVE_LOW, -1, "EC interrupt"},
{CR50_IRQ.id, ACTIVE_HIGH, -1, "TPM interrupt"},
{GPIO_EN_SPK_AMP.id, ACTIVE_HIGH, -1, "speaker enable"},
};
lb_add_gpios(gpios, chromeos_gpios, ARRAY_SIZE(chromeos_gpios));
}

View File

@@ -23,6 +23,7 @@
#define EC_IN_RW GPIO(PERIPHERAL_EN14)
#define CR50_IRQ GPIO(PERIPHERAL_EN3)
#define GPIO_RESET GPIO(PERIPHERAL_EN8)
#define GPIO_EN_SPK_AMP GPIO(PERIPHERAL_EN12)
void setup_chromeos_gpios(void);

View File

@@ -16,6 +16,7 @@
#include <device/device.h>
#include <soc/gpio.h>
#include <soc/mmu_operations.h>
#include <soc/mtcmos.h>
#include <soc/usb.h>
static void configure_emmc(void)
@@ -37,10 +38,22 @@ static void configure_usb(void)
setup_usb_host();
}
static void configure_audio(void)
{
/* Audio PWR*/
mtcmos_audio_power_on();
/* SoC I2S */
gpio_set_mode(GPIO(CAM_RST0), PAD_CAM_RST0_FUNC_I2S2_LRCK);
gpio_set_mode(GPIO(CAM_PDN1), PAD_CAM_PDN1_FUNC_I2S2_BCK);
gpio_set_mode(GPIO(CAM_PDN0), PAD_CAM_PDN0_FUNC_I2S2_MCK);
gpio_set_mode(GPIO(EINT3), PAD_EINT3_FUNC_I2S3_DO);
}
static void mainboard_init(struct device *dev)
{
configure_emmc();
configure_usb();
configure_audio();
}
static void mainboard_enable(struct device *dev)

View File

@@ -17,6 +17,7 @@
#include <soc/emi.h>
#include <soc/mmu_operations.h>
#include <soc/mt6358.h>
#include <soc/pll.h>
#include <soc/rtc.h>
#include "early_init.h"
@@ -28,6 +29,7 @@ void platform_romstage_main(void)
mainboard_early_init();
mt6358_init();
mt_pll_raise_ca53_freq(1989 * MHz);
rtc_boot();
mt_mem_init(get_sdram_config());
mtk_mmu_after_dram();

View File

@@ -25,19 +25,18 @@
#include <arch/io.h>
#include <arch/interrupt.h>
#include <boot/coreboot_tables.h>
#include "onboard.h"
#include "ec.h"
#include <southbridge/intel/bd82x6x/pch.h>
#include <northbridge/intel/sandybridge/gma.h>
#include <smbios.h>
#include <device/pci.h>
#include <ec/google/chromeec/ec.h>
#include <cpu/x86/tsc.h>
#include <cpu/x86/cache.h>
#include <cpu/x86/mtrr.h>
#include <cpu/x86/msr.h>
#include <edid.h>
#include "ec.h"
#include "onboard.h"
#include "i915io.h"
enum {

View File

@@ -44,7 +44,7 @@ void mainboard_save_dimm_info(void)
if (!CONFIG(DRAM_PART_NUM_ALWAYS_IN_CBI)) {
/* Fall back on part numbers encoded in lp4cfg array. */
if (board_id() < CONFIG_DRAM_PART_IN_CBI_BOARD_ID_MIN) {
if ((int)board_id() < CONFIG_DRAM_PART_IN_CBI_BOARD_ID_MIN) {
save_dimm_info_by_sku_config();
return;
}

View File

@@ -210,7 +210,7 @@ const struct lpddr4_cfg *__weak variant_lpddr4_config(void)
if (!CONFIG(DRAM_PART_NUM_ALWAYS_IN_CBI)) {
/* Fall back non cbi memory config. */
if (board_id() < CONFIG_DRAM_PART_IN_CBI_BOARD_ID_MIN)
if ((int)board_id() < CONFIG_DRAM_PART_IN_CBI_BOARD_ID_MIN)
return &non_cbi_lp4cfg;
}

View File

@@ -10,6 +10,7 @@ config BOARD_GOOGLE_BASEBOARD_POPPY
select EC_GOOGLE_CHROMEEC_LPC
select HAVE_ACPI_RESUME
select HAVE_ACPI_TABLES
select INTEL_GMA_HAVE_VBT if BOARD_GOOGLE_NAMI
select INTEL_LPSS_UART_FOR_CONSOLE
select MAINBOARD_HAS_CHROMEOS
select MAINBOARD_USES_FSP2_0
@@ -151,6 +152,7 @@ config VARIANT_SPECIFIC_OPTIONS_ATLAS
select DRIVERS_I2C_MAX98373
select DRIVERS_I2C_DA7219
select DRIVERS_SPI_ACPI
select DRIVERS_USB_ACPI
select EXCLUDE_NATIVE_SD_INTERFACE
select MAINBOARD_HAS_SPI_TPM_CR50
select VARIANT_HAS_CAMERA_ACPI

View File

@@ -265,7 +265,30 @@ chip soc/intel/skylake
device pci 00.0 on end # Host Bridge
device pci 02.0 on end # Integrated Graphics Device
device pci 13.0 off end # Integrated Sensor Hub
device pci 14.0 on end # USB xHCI
device pci 14.0 on
chip drivers/usb/acpi
register "desc" = ""Root Hub""
register "type" = "UPC_TYPE_HUB"
device usb 0.0 on
chip drivers/usb/acpi
register "desc" = ""USB Type C Port 1""
register "type" = "UPC_TYPE_C_USB2_SS_SWITCH"
device usb 2.0 on end
end
chip drivers/usb/acpi
register "desc" = ""Bluetooth""
register "type" = "UPC_TYPE_INTERNAL"
register "reset_gpio" = "ACPI_GPIO_OUTPUT_ACTIVE_LOW(GPP_E2)"
device usb 2.2 on end
end
chip drivers/usb/acpi
register "desc" = ""USB Type C Port 2""
register "type" = "UPC_TYPE_C_USB2_SS_SWITCH"
device usb 2.4 on end
end
end
end
end # USB xHCI
device pci 14.1 on end # USB xDCI (OTG)
device pci 14.2 on end # Thermal Subsystem
device pci 15.0 on

View File

@@ -43,3 +43,6 @@ oem.bin-file := $(call strip_quotes,$(CONFIG_OEM_BIN_FILE))
oem.bin-type := raw
$(call add_vbt_to_cbfs, vbt-bard.bin, bard-data.vbt)
$(call add_vbt_to_cbfs, vbt-akali.bin, akali-data.vbt)
$(call add_vbt_to_cbfs, vbt-pantheon.bin, pantheon-data.vbt)
$(call add_vbt_to_cbfs, vbt-vayne.bin, vayne-data.vbt)

Binary file not shown.

View File

@@ -16,7 +16,6 @@ config BOARD_GOOGLE_BASEBOARD_SARIEN
select MAINBOARD_HAS_CHROMEOS
select MAINBOARD_HAS_I2C_TPM_CR50
select MAINBOARD_HAS_TPM2
select SOC_INTEL_COMMON_ACPI_EC_PTS_WAK
select SOC_INTEL_WHISKEYLAKE
select SOC_INTEL_COMMON_BLOCK_HDA_VERB
select SOC_INTEL_COMMON_BLOCK_SMM_ESPI_DISABLE

View File

@@ -40,6 +40,8 @@ DefinitionBlock(
#include <soc/intel/cannonlake/acpi/northbridge.asl>
#include <soc/intel/cannonlake/acpi/southbridge.asl>
}
/* Per board variant mainboard hooks. */
#include <variant/acpi/mainboard.asl>
}
#if CONFIG(CHROMEOS)

View File

@@ -37,10 +37,10 @@ chip soc/intel/cannonlake
register "tdp_pl2_override" = "51"
register "Device4Enable" = "1"
register "AcousticNoiseMitigation" = "1"
register "SlowSlewRateForIa" = "0"
register "SlowSlewRateForGt" = "0"
register "SlowSlewRateForIa" = "2"
register "SlowSlewRateForGt" = "2"
register "SlowSlewRateForSa" = "0"
register "SlowSlewRateForFivr" = "0"
register "SlowSlewRateForFivr" = "2"
# Enable eDP device
register "DdiPortEdp" = "1"
# Enable HPD for DDI ports B/C
@@ -161,7 +161,7 @@ chip soc/intel/cannonlake
#| I2C4 | H1 TPM |
#+-------------------+---------------------------+
register "tcc_offset" = "10"
register "tcc_offset" = "1"
register "common_soc_config" = "{
.chipset_lockdown = CHIPSET_LOCKDOWN_COREBOOT,
@@ -349,11 +349,15 @@ chip soc/intel/cannonlake
device pci 1c.5 off end # PCI Express Port 6
device pci 1c.6 off end # PCI Express Port 7
device pci 1c.7 off end # PCI Express Port 8
device pci 1d.0 on end # PCI Express Port 9
device pci 1d.0 on
smbios_slot_desc "SlotTypeM2Socket1_SD" "SlotLengthOther" "2230" "SlotDataBusWidth1X"
end # PCI Express Port 9
device pci 1d.1 on end # PCI Express Port 10
device pci 1d.2 on end # PCI Express Port 11
device pci 1d.3 off end # PCI Express Port 12
device pci 1d.4 on end # PCI Express Port 13 (x4)
device pci 1d.4 on
smbios_slot_desc "SlotTypeM2Socket3" "SlotLengthOther" "2280" "SlotDataBusWidth4X"
end # PCI Express Port 13 (x4)
device pci 1e.0 off end # UART #0
device pci 1e.1 off end # UART #1
device pci 1e.2 off end # GSPI #0

View File

@@ -13,14 +13,14 @@
* GNU General Public License for more details.
*/
#define DPTF_CPU_PASSIVE 96
#define DPTF_CPU_CRITICAL 103
#define DPTF_CPU_PASSIVE 90
#define DPTF_CPU_CRITICAL 105
/* Skin Sensor for CPU VR temperature monitor */
#define DPTF_TSR0_SENSOR_ID 1
#define DPTF_TSR0_SENSOR_NAME "Skin"
#define DPTF_TSR0_PASSIVE 56
#define DPTF_TSR0_CRITICAL 108
#define DPTF_TSR0_PASSIVE 60
#define DPTF_TSR0_CRITICAL 105
/* Memory Sensor for DDR temperature monitor */
#define DPTF_TSR1_SENSOR_ID 2
@@ -31,24 +31,24 @@
/* M.2 Sensor for Ambient temperature monitor */
#define DPTF_TSR2_SENSOR_ID 3
#define DPTF_TSR2_SENSOR_NAME "Ambient"
#define DPTF_TSR2_PASSIVE 50
#define DPTF_TSR2_CRITICAL 95
#define DPTF_TSR2_PASSIVE 37
#define DPTF_TSR2_CRITICAL 80
#undef DPTF_ENABLE_FAN_CONTROL
#undef DPTF_ENABLE_CHARGER
Name (DTRT, Package () {
/* CPU Throttle Effect on CPU */
Package () { \_SB.PCI0.TCPU, \_SB.PCI0.TCPU, 100, 10, 0, 0, 0, 0 },
Package () { \_SB.PCI0.TCPU, \_SB.PCI0.TCPU, 500, 100, 0, 0, 0, 0 },
/* CPU Throttle Effect on Skin (TSR0) */
Package () { \_SB.PCI0.TCPU, \_SB.DPTF.TSR0, 100, 600, 0, 0, 0, 0 },
Package () { \_SB.PCI0.TCPU, \_SB.DPTF.TSR0, 500, 30, 0, 0, 0, 0 },
/* CPU Throttle Effect on DDR (TSR1) */
Package () { \_SB.PCI0.TCPU, \_SB.DPTF.TSR1, 100, 90, 0, 0, 0, 0 },
Package () { \_SB.PCI0.TCPU, \_SB.DPTF.TSR1, 100, 50, 2, 0, 0, 0 },
/* CPU Throttle Effect on Ambient (TSR2) */
Package () { \_SB.PCI0.TCPU, \_SB.DPTF.TSR2, 100, 600, 0, 0, 0, 0 },
Package () { \_SB.PCI0.TCPU, \_SB.DPTF.TSR2, 1000, 100, 1, 0, 0, 0 },
})
Name (MPPC, Package ()

View File

@@ -0,0 +1,44 @@
/*
* This file is part of the coreboot project.
*
* Copyright 2019 Intel Corp.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; version 2 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#define CAM_EN GPP_B11 /* Active low */
#define TS_PD GPP_E7
/* Method called from LPIT prior to enter s0ix state */
Method (MS0X, 1)
{
If (Arg0) {
/* Turn off camera power */
\_SB.PCI0.STXS (CAM_EN)
} Else {
/* Turn on camera power */
\_SB.PCI0.CTXS (CAM_EN)
}
}
/* Method called from _PTS prior to enter sleep state */
Method (MPTS, 1)
{
\_SB.PCI0.LPCB.EC0.PTS (Arg0)
/* Clear touch screen pd pin to avoid leakage */
\_SB.PCI0.CTXS (TS_PD)
}
/* Method called from _WAK prior to wakeup */
Method (MWAK, 1)
{
\_SB.PCI0.LPCB.EC0.WAK (Arg0)
}

View File

@@ -378,11 +378,15 @@ chip soc/intel/cannonlake
device pci 1c.5 off end # PCI Express Port 6
device pci 1c.6 off end # PCI Express Port 7
device pci 1c.7 on end # PCI Express Port 8
device pci 1d.0 on end # PCI Express Port 9
device pci 1d.0 on
smbios_slot_desc "SlotTypeM2Socket1_SD" "SlotLengthOther" "2230" "SlotDataBusWidth1X"
end # PCI Express Port 9
device pci 1d.1 on end # PCI Express Port 10
device pci 1d.2 off end # PCI Express Port 11
device pci 1d.3 off end # PCI Express Port 12
device pci 1d.4 on end # PCI Express Port 13 (x4)
device pci 1d.4 on
smbios_slot_desc "SlotTypeM2Socket3" "SlotLengthOther" "2280" "SlotDataBusWidth4X"
end # PCI Express Port 13 (x4)
device pci 1e.0 off end # UART #0
device pci 1e.1 off end # UART #1
device pci 1e.2 off end # GSPI #0

View File

@@ -31,9 +31,9 @@ static const struct pad_config gpio_table[] = {
/* CLKOUT_LPC1 */ PAD_NC(GPP_A10, NONE),
/* PME# */ PAD_NC(GPP_A11, NONE),
/* BM_BUSY# */ PAD_NC(GPP_A12, NONE),
/* SUSWARN# */ PAD_CFG_GPO(GPP_A13, 0, DEEP), /* Card reader D3 cold */
/* ESPI_RESET# */
/* SUSACK# */ PAD_CFG_GPO(GPP_A15, 0, DEEP), /* Card reader D3 cold */
/* SD_1P8_SEL */ PAD_NC(GPP_A16, NONE),
/* SD_PWR_EN# */ PAD_NC(GPP_A17, NONE),
/* ISH_GP0 */ PAD_NC(GPP_A18, NONE),
@@ -224,9 +224,12 @@ static const struct pad_config gpio_table[] = {
/* Early pad configuration in bootblock */
static const struct pad_config early_gpio_table[] = {
/* M2_SKT2_CFG0 */ PAD_CFG_GPO(GPP_H12, 0, DEEP), /* D3 cold RST */
/* SUSWARN# */ PAD_CFG_GPO(GPP_A13, 0, DEEP), /* Card reader D3 cold */
/* SUSACK# */ PAD_CFG_GPO(GPP_A15, 0, DEEP), /* Card reader D3 cold */
/* UART2_RXD */ PAD_CFG_NF(GPP_C20, NONE, DEEP, NF1), /* SERVOTX_UART */
/* UART2_TXD */ PAD_CFG_NF(GPP_C21, NONE, DEEP, NF1), /* SERVORX_UART */
/* SSD RESET pin will stay low first */
/* M2_SKT2_CFG0 */ PAD_CFG_GPO(GPP_H12, 0, DEEP), /* D3 cold RST */
/* I2C4_SDA */ PAD_CFG_NF(GPP_H8, NONE, DEEP, NF1), /* I2C_SDA_H1 */
/* I2C4_SCL */ PAD_CFG_NF(GPP_H9, NONE, DEEP, NF1), /* I2C_SCL_H1 */
/* DMIC_DATA1 */ PAD_CFG_GPI_APIC(GPP_D18, NONE, PLTRST,
@@ -236,9 +239,8 @@ static const struct pad_config early_gpio_table[] = {
/* CPU_GP0 */ PAD_CFG_GPI(GPP_E3, NONE, DEEP), /* MEM_INTERLEAVED */
/* SATALED# */ PAD_CFG_GPI(GPP_E8, NONE, DEEP), /* RECOVERY# */
/* DDPD_HPD2 */ PAD_CFG_GPI(GPP_E15, NONE, DEEP), /* H1_FLASH_WP */
/* SSD RESET need to stay low first */
/* M2_SKT2_CFG0 */ PAD_CFG_GPO(GPP_H12, 1, DEEP), /* D3 cold RST */
/* PWRBTN# */ PAD_CFG_NF(GPD3, UP_20K, DEEP, NF1), /* SIO_PWRBTN# */
/* M2_SKT2_CFG0 */ PAD_CFG_GPO(GPP_H12, 1, DEEP), /* D3 cold RST */
};
const struct pad_config *variant_gpio_table(size_t *num)

Some files were not shown because too many files have changed in this diff Show More