summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTom Hughes <tomhughes@chromium.org>2020-04-06 11:28:55 -0700
committerCommit Bot <commit-bot@chromium.org>2020-07-10 22:25:15 +0000
commitecbfeecacd7a7861064c81eb7cabdd5c1b64e240 (patch)
treeb2e6c16a8098604fe7d50bb5f059811b32f7e644
parent520c628294c612c57f65579fd66d3bcd3ca0ff02 (diff)
downloadchrome-ec-ecbfeecacd7a7861064c81eb7cabdd5c1b64e240.tar.gz
docs/case_closed_debugging_cr50: Refactor
Refactor the CCD documentation so it's easier for non-experts to understand. BUG=none TEST=view in gitiles Signed-off-by: Tom Hughes <tomhughes@chromium.org> Change-Id: I89ba8fd5906119c4acfe1a555db5b7872dd949a9 Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/ec/+/2137929 (cherry picked from commit 2ba6907508ecfc223c047db686fe459c9596f026) Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/ec/+/2278523 Tested-by: Vadim Bendebury <vbendeb@chromium.org>
-rw-r--r--docs/case_closed_debugging_cr50.md1187
1 files changed, 562 insertions, 625 deletions
diff --git a/docs/case_closed_debugging_cr50.md b/docs/case_closed_debugging_cr50.md
index e46bca66c6..0e244c15a0 100644
--- a/docs/case_closed_debugging_cr50.md
+++ b/docs/case_closed_debugging_cr50.md
@@ -1,349 +1,308 @@
# Google Security Chip (GSC) Case Closed Debugging (CCD)
-Cr50 is the firmware that runs on the Google Security Chip. It has support for
-Case Closed Debugging (CCD). This support is complete enough to replace servo.
-This doc explains how to setup CCD, so you can access all of the necessary
-features to develop firmware on your device or control different components.
-Please run through the basic setup steps before trying to flash the AP firmware.
-CCD could help recover your device if you flash broken firmware, but **if you
-brick your device before setting up CCD, you may not be able to enable it**.
+Cr50 is the firmware that runs on the Google Security Chip (GSC), which has
+support for [Case Closed Debugging](CCD).
-[TOC]
-
-# Background
-
-Cr50 CCD was designed to restrict CCD access to device owners. There are **CCD
-privilege levels** that can be used to enable access to different CCD
-capabilities **Open, Unlocked, Locked**.
-
-All CCD functionality has been assigned to different **CCD capabilities**.
-Capability settings can be modified to require certain privilege levels to
-access the each capability. Setting a capability requirement to **IfOpened**
-will require a level of **Open** to access that capability. A requirement of
-**UnlessLocked** will require the device to be **Open** or **Unlocked** to
-access the capability. Setting the requirement to **Always** will make the
-capability always accessible.
-
-Owners can use these settings to customize the CCD so it is as open or
-restricted as they want.
-
-# CCD Capabilities
-
-Cr50 is locked by default. Here are all of the Capabilities and their default
-settings.
-
-Capability | Default | Function
---------------- | -------- | --------
-UartGscRxAPTx | Always | controls reading from the AP console
-UartGscTxAPRx | Always | controls writing to the AP console
-UartGscRxECTx | Always | controls reading from the EC console
-UartGscTxECRx | IfOpened | controls writing to the EC console
-FlashAP | IfOpened | controls flashing the AP
-FlashEC | IfOpened | controls flashing the EC
-OverrideWP | IfOpened | controls controlling write protect
-RebootECAP | IfOpened | controls rebooting the EC/AP from the cr50 console
-GscFullConsole | IfOpened | controls access to restricted Cr50 console commands
-UnlockNoReboot | Always | controls unlocking Cr50 without rebooting the AP
-UnlockNoShortPP | Always | controls unlocking Cr50 without physical presence
-OpenNoTPMWipe | IfOpened | controls opening Cr50 without wiping the TPM
-OpenNoLongPP | IfOpened | controls opening Cr50 without physical presence
-BatteryBypassPP | Always | controls opening cr50 without physical presence and dev mode if the battery is removed
-UpdateNoTPMWipe | Always | controls updating cr50 without wiping the TPM
-I2C | IfOpened | controls access to the I2C master (used for measuring power)
-FlashRead | Always | controls dumping a hash of the AP or EC flash
-OpenNoDevMode | IfOpened | controls opening cr50 without dev mode
-OpenFromUSB | IfOpened | controls opening cr50 from USB
-
-# CCD Setup
-
-Some basic CCD functionality is accessible by default. There is read-only access
-to the EC console and read-write access to the AP console. There are some basic
-cr50 console commands you can run.
-
-Cr50 CCD needs to be opened to access all CCD functionality or to modify
-capability settings so the device doesn't need to be open to access CCD
-functionality.
-
-## Prerequisites
-
-Cr50 needs to be newer than 0.3.9 or 0.4.9 to setup ccd. The 3 in the major
-version means it's a MP image and 0.4.X is a prePVT image. There aren't many
-differences between the MP and prePVT versions of images. It is just a little
-easier to CCD open prePVT images. You can't run prePVT images on MP devices, so
-if you're trying to update to .prepvt and it fails try using .prod.
-
-* Sync chroot to TOT (run `repo sync` in chromiumos directory) update `servod`
- and `gsctool` in chroot
-
- ```bash
- (chroot) $ sudo emerge hdctools ec-devutils servo-firmware chromeos-cr50 chromeos-cr50-scripts
- ```
-
-* Update servo v4 firmware
-
- ```bash
- (chroot) $ sudo servo_updater -b servo_v4
- ```
-
-* Ensure cr50 firmware is up to date. You can run these `gsctool` commands
- from the AP console or you can run them as root from inside the chroot if
- suzyq is connected.
-
- * If you're doing this from the AP, install a test image newer than M66.
- * check the cr50 version
+This document explains how to setup CCD, so you can access all of the necessary
+features to develop firmware on your Chrome OS device, access
+[debug consoles][consoles], and [disable hardware write protect][hw-wp].
- ```bash
- (dut) $ sudo gsctool -a -f
- ```
-
- * If the RW version is greater than 0.(3|4).9 then you don't need to
- update cr50. If it's not, then you need to update cr50.
-
- * Update cr50.
-
- ```bash
- (dut) $ sudo gsctool -a /opt/google/cr50/firmware/cr50.bin.prod
- ```
-
- * Check the cr50 version again to make sure it's now newer than 0.X.9
+[TOC]
-* Ensure power isolation on servo v4
+## Overview
- * Plug USB-C power into servo v4 for dut pass though
- * Green LED will light up when plugged into DUT.
+Cr50 CCD was designed to restrict CCD access to device owners and is implemented
+through **CCD privilege levels** ([`Open`], [`Unlocked`], [`Locked`]) that can
+be used to enable access to different **[CCD capabilities][cap]**. Capability
+settings can be modified to require certain privilege levels to access each
+capability. Device owners can use these settings to customize CCD so that it is
+as open or restricted as they want.
+
+Cr50 CCD exposes [3 debug consoles][consoles]: AP, EC, and Cr50 as well as
+control over [Hardware Write Protect][hw-wp]. Cr50 CCD also allows
+[flashing the AP firmware] or [flashing the EC firmware].
+
+### Capability and Privilege Levels {#cap-priv}
+
+Privilege Levels |
+---------------- |
+`Open` |
+`Unlocked` |
+`Locked` |
+
+Capability Setting | Definition
+------------------ | ----------
+`IfOpened` | Specified capability is allowed if Cr50 Privilege Level is `Open`.
+`UnlessLocked` | Specified capability is allowed unless Cr50 Privilege Level is `Locked`.
+`Always` | Specified capability is always allowed, regardless of Cr50 Privilege Level.
+
+Capability Setting | Privilege Level Required
+------------------ | ----------------------------------------
+`IfOpened` | `Open`
+`UnlessLocked` | `Open` or `Unlocked`
+`Always` | `Open`, `Unlocked`, `Locked` (any state)
+
+## CCD Capabilities {#cap}
+
+The default Cr50 privilege level is [`Locked`] with the following capability
+settings:
+
+Capability | Default | Function
+----------------- | ---------- | --------
+`UartGscRxAPTx` | `Always` | AP console read access
+`UartGscTxAPRx` | `Always` | AP console write access
+`UartGscRxECTx` | `Always` | EC console read access
+`UartGscTxECRx` | `IfOpened` | EC console write access
+[`FlashAP`] | `IfOpened` | Allows flashing the AP
+[`FlashEC`] | `IfOpened` | Allows flashing the EC
+[`OverrideWP`] | `IfOpened` | Override hardware write protect
+`RebootECAP` | `IfOpened` | Allow rebooting the EC/AP from the Cr50 console
+`GscFullConsole` | `IfOpened` | Allow access to restricted Cr50 console commands
+`UnlockNoReboot` | `Always` | Allow unlocking Cr50 without rebooting the AP
+`UnlockNoShortPP` | `Always` | Allow unlocking Cr50 without physical presence
+`OpenNoTPMWipe` | `IfOpened` | Allow opening Cr50 without wiping the TPM
+`OpenNoLongPP` | `IfOpened` | Allow opening Cr50 without physical presence
+`BatteryBypassPP` | `Always` | Allow opening Cr50 without physical presence and developer mode if the battery is removed
+`UpdateNoTPMWipe` | `Always` | Allow updating Cr50 without wiping the TPM
+`I2C` | `IfOpened` | Allow access to the I2C master (used for measuring power)
+`FlashRead` | `Always` | Allow dumping a hash of the AP or EC flash
+`OpenNoDevMode` | `IfOpened` | Allow opening Cr50 without developer mode
+`OpenFromUSB` | `IfOpened` | Allow opening Cr50 from USB
+
+## Consoles {#consoles}
+
+Cr50 presents 3 consoles through CCD: AP, EC, and Cr50, each of which show up on
+your host machine as a `/dev/ttyUSBX` device when a debug cable ([Suzy-Q] or
+[Type-C Servo v4]) is plugged in to the DUT.
+
+Console | Default access | Capability Name
+------- | ------------------------------------------- | ---------------
+Cr50 | always read/write, but commands are limited | `GscFullConsole` enables the full set of Cr50 console commands
+AP | read/write | `UartGscRxAPTx` / `UartGscTxAPRx`
+EC | read-only | `UartGscRxECTx` / `UartGscTxECRx`
+
+### Connecting to a Console
+
+When a debug cable ([Suzy-Q] or [Type-C Servo v4]) is plugged in to the DUT, the
+3 consoles will show up as `/dev/ttyUSBX` devices. You can connect to them with
+your favorite terminal program (e.g., `minicom`, `screen`, etc). You can also
+use the [`usb_console`] command to connect to Cr50 (`18d1:5014`) and specify the
+interface to choose between the consoles.
-## Basic Steps for CCD setup
+```bash
+# Install `usb_console`
+(chroot) sudo emerge ec-devutils
+```
-1. Use the general [setup](case_closed_debugging.md#Setup) instructions to
- connect Suzy-Q and access the Cr50 console. The Cr50 console will be the
- lowest `/dev/ttyUSB*` device created by Cr50 or `/dev/google/<device
- name>/serial/Shell`
+```bash
+# Connect to Cr50 console
+(chroot) $ usb_console -d 18d1:5014
+```
-1. [Open CCD](#Open-CCD)
+```bash
+# Connect to AP console
+(chroot) $ usb_console -d 18d1:5014 -i 1
+```
-1. [Modify capabilities](#Enable-Open-Without-Requiring-Device-to-Boot) to make
- it easier to open cr50 or access necessary capabilities - this step is
- optional, but **the open state will be lost if cr50 reboots or the device
- loses power**. If your use of CCD will possibly brick the device, it is
- recommended you modify the capability settings or set a ccd password, so you
- can reopen the device.
+```bash
+# Connect to EC console
+(chroot) $ usb_console -d 18d1:5014 -i 2
+```
-1. Use CCD
+#### Using "servod" to access the console
-## Open CCD
+[`servod`] can be used to create alternative console devices when combined with
+a [Servo].
-The first cr50 image with CCD support was 0.3.9. If you are not running 0.3.9,
-you need to download the image and update cr50 from the AP or using Suzy-Q.
-https://storage.googleapis.com/chromeos-localmirror/distfiles/cr50.r0.0.10.w0.3.9.tbz2
+First, make sure your [servo firmware is updated][update servo v4].
-You can download the cr50 image and then flash cr50 using Suzy-Q from the chroot
+Next, start [`servod`]:
```bash
-(chroot) $ sudo gsctool cr50.r0.0.10.w0.3.9/cr50.bin.prod
+(chroot) $ sudo servod -b $BOARD
```
-If you are only briefly using ccd and aren’t doing anything that may brick the
-device, you can probably just stick to opening cr50. **The open state will be
-lost after cr50 reboot. If you don’t want to have to reopen cr50, you may want
-to setup the ccd capabilities so you can use them without needing cr50 to be
-open.**
-
-### Standard Process (Requires Booting to Kernel)
+Then use `dut-control` to display the console devices:
-If your device can boot, you can open Cr50 by entering dev mode and then sending
-the ccd open command from the kernel.
+```bash
+(chroot) $ dut-control cr50_uart_pty ec_uart_pty cpu_uart_pty
+```
-#### Enter dev mode
+Connect to the console devices with your favorite terminal program (e.g.,
+`minicom`, `screen`, etc.).
-Entering dev mode has to be done manually. Using the gbb flags to force dev mode
-will not work.
+## CCD Open {#ccd-open}
-1. First, on a root shell on the device, check the force dev mode flag isn’t
- set GBB flags by running. If you can’t access the shell, because you aren’t
- in dev mode, then you’re fine. You can skip steps 1, 2, and 3.
+Some basic CCD functionality is accessible by default: read-only access to the
+EC console, read-write access to the AP console, and a few basic Cr50 console
+commands. Note that while Cr50 has read-write access to the AP console by
+default, the AP console itself is disabled for production devices.
- ```bash
- (chroot) $ /usr/share/vboot/bin/get_gbb_flags.sh
- ```
+In order to access all CCD functionality or to modify capability settings, Cr50
+CCD needs to be [`Open`].
-1. Clear `0x8` from the GBB flags and set the new value
+1. Connect to the Cr50 console by connecting a [Suzy-Q] or [Type-C Servo v4] to
+ the DUT and running the following command:
```bash
- (chroot) $ /usr/share/vboot/bin/set_gbb_flags.sh $OLD_FLAG_VALUE & ~0x8
+ (chroot) $ usb_console -d 18d1:5014
```
-1. Reboot the device
-
-1. Put the device into [Recovery Mode].
+ *** note
+ **NOTE**: If another program is already connected to the Cr50 console,
+ you'll see `tx [Errno 16] Resource Busy`. For example, this will happen if
+ [`servod`] is running.
+ ***
-1. Enable [Developer Mode].
-
-1. Verify Cr50 knows the device is in dev mode. The TPM state will print
- `dev_mode` if cr50 knows the device is in dev mode. If it doesn’t say
- `dev_mode`, ccd open will fail. If you see "`TPM: dev_mode`" you are okay to
- CCD open now. **If you don’t see `TPM: dev_mode`, recheck the gbb flags to
- make sure they aren’t forcing dev mode. Retry the manual entry of dev
- mode.**
+1. At the Cr50 console, use the `version` command to make sure you have a
+ recent enough version to use CCD. The relevant version is either `RW_A` or
+ `RW_B`, whichever has the asterisk next to it:
```
- cr50 > ccd
- State: Locked
- Password: none
- Flags: 0x000001
- Capabilities: 0000000000000000
- UartGscRxAPTx Y 0=Default (Always)
- UartGscTxAPRx Y 0=Default (Always)
- UartGscRxECTx Y 0=Default (Always)
- UartGscTxECRx - 0=Default (IfOpened)
- FlashAP - 0=Default (IfOpened)
- FlashEC - 0=Default (IfOpened)
- OverrideWP - 0=Default (IfOpened)
- RebootECAP - 0=Default (IfOpened)
- GscFullConsole - 0=Default (IfOpened)
- UnlockNoReboot Y 0=Default (Always)
- UnlockNoShortPP Y 0=Default (Always)
- OpenNoTPMWipe - 0=Default (IfOpened)
- OpenNoLongPP - 0=Default (IfOpened)
- BatteryBypassPP Y 0=Default (Always)
- UpdateNoTPMWipe Y 0=Default (Always)
- I2C - 0=Default (IfOpened)
- FlashRead Y 0=Default (Always)
- OpenNoDevMode - 0=Default (IfOpened)
- OpenFromUSB - 0=Default (IfOpened)
- TPM: dev_mode <==== This is the important part
- Use 'ccd help' to print subcommands
+ cr50 > version
+
+ Chip: g cr50 B2-C
+ Board: 0
+ RO_A: * 0.0.10/29d77172
+ RO_B: 0.0.10/c2a3f8f9
+ RW_A: * 0.3.23/cr50_v1.9308_87_mp.320-aa1dd98 <---- This is the version
+ RW_B: 0.3.18/cr50_v1.9308_87_mp.236-8052858
+ BID A: 00000000:00000000:00000000 Yes
+ BID B: 00000000:00000000:00000000 Yes
+ Build: 0.3.23/cr50_v1.9308_87_mp.320-aa1dd98
+ tpm2:v1.9308_26_0.36-d1631ea
+ cryptoc:v1.9308_26_0.2-a4a45f5
+ 2019-10-14 19:18:05 @chromeos-ci-legacy-us-central2
```
-#### Run ccd open
-
-You can start the open process from the AP. Once you start the process, you will
-need to press the power button when prompted open cr50.
+1. Production (`MP`) versions of Cr50 firmware use a [minor version][semver] of
+ `3`: `0.3.x`. Production firmware versions `0.3.9` or newer support CCD.
-1. Start the ccd open process from the AP.
-
- ```bash
- (chroot) $ gsctool -a -o
- ```
+ Development (`PrePVT`) versions of Cr50 firmware use a minor version of
+ `4`: `0.4.x`. Development firmware versions `0.4.9` or newer support CCD.
-1. Over the next 5 minutes you will be prompted to press the power button.
+ Your device likely supports CCD if it was manufactured in the last few
+ years. If you have an older version, follow the [Updating Cr50] instructions
+ before continuing.
-1. After the process is finished, use ‘ccd’ on the cr50 console to verify the
- state is open.
+1. Put the device into [Recovery Mode] and enable [Developer Mode].
-The Open setting will be lost whenever cr50 reboots. Make sure to setup ccd so
-you will be able to recover the device even if Open is lost. To open cr50 you
-need access to the AP. If your debugging will make the AP inaccessible and you
-want to ensure that you can recover the device, you either need to modify the
-capability settings so you can access the capabilities necessary to recover the
-device while cr50 is locked or you need to modify the capabilities so you don't
-need the AP to open cr50.
+ *** note
+ **NOTE**: Developer Mode has to be enabled as described. Using GBB flags to
+ force Developer Mode will not work.
+ ***
-If you need to reflash the AP or EC, you can set the FlashEC or FlashAP
-capabilities to Always.
+ If you can't put your device into [Developer Mode] because it doesn't boot,
+ follow the [CCD Open Without Booting the Device] instructions.
-If you want to be able to open cr50 without the AP, set OpenNoDevMode and
-OpenFromUSB to Always.
+1. Verify Cr50 knows the device is in [Developer Mode] by finding `TPM:
+ dev_mode` in the Cr50 console `ccd` command output:
-### CCD Open Without Booting the Device
+ ```
+ cr50 > ccd
+ ...
+ TPM: dev_mode <==== This is the important part
+ ...
+ ```
-If you can’t boot the device, you won’t be able to enter dev mode and send the
-open command from the AP. You will need to follow some non-standard methods to
-open the device. If you have enabled ccd before, cr50 may be configured in a way
-that you can still open cr50. If you haven't setup CCD before, you will need to
-remove the battery to enable CCD.
+1. Start the CCD open process from the AP.
-#### Can remove the Battery
+ ```bash
+ (dut) $ gsctool -a -o
+ ```
-If you can remove the battery, you can bypass the AP command/dev mode
-requirements. `ccd open` is allowed from the console if FWMP doesn’t disable ccd
-and the battery is disconnected. This is the most universal method and will work
-even if you haven’t enabled ccd before. Some devices are glued shut if you
-can’t/don’t want to unglue your device do not rely on this method. Setup ccd
-correctly before flashing the AP/EC.
+1. Over the next 5 minutes you will be prompted to press the power button
+ multiple times. After the last power button press the device will reboot.
-1. Disconnect the battery
+ *** note
+ **WARNING**: Opening CCD causes Cr50 to forget that it is in
+ [Developer Mode], so when the device reboots, it will say that the OS
+ image is invalid. Use the key combinations to enter [Recovery Mode] and
+ re-enable [Developer Mode]. See [this bug] for details.
+ ***
-1. Send `ccd open` from the cr50 console.
+1. Use the `ccd` command on the Cr50 console to verify the state is [`Open`]:
-#### CCD testlab is enabled
+ ```
+ cr50 > ccd
-You can check if `testlab` is enabled cr50 from the console.
+ State: Opened
+ ...
+ ```
-```
-cr50 > ccd testlab
- CCD test lab mode enabled
-```
+1. **The [`Open`] state is lost if Cr50 reboots, the device loses power (e.g.,
+ battery runs out and AC is not plugged in), or the battery is removed. Note
+ that Cr50 does not reboot when the system reboots; it only reboots if it is
+ updated, the devices loses power, the battery runs out, or it crashes**. If
+ you plan on [flashing the AP firmware] or [flashing the EC firmware], it is
+ recommended you modify the capability settings or set a CCD password, so you
+ can reopen the device in the case that you accidentally brick it with bad
+ firmware. The simplest way to do this is to reset to factory settings and
+ enable testlab mode:
-If it’s enabled, you can open cr50 from the console without physical presence.
+ ```
+ cr50 > ccd reset factory
+ ```
-```
-cr50 > ccd testlab open
-```
+ ```
+ cr50 > ccd testlab enable
+ ```
-#### OpenNoDevMode and OpenFromUSB are set to Always
+ For full details, see the section on [CCD Open Without Booting the Device].
-This requires >=0.3.10. If these capabilities are set, you will be able to open
-cr50 from the console without dev mode.
+## Configuring CCD Capability Settings
- cr50 > ccd open
+Cr50 capabilities allow you to configure CCD to restrict or open the device as
+much as you want. You can use the `ccd` command on the Cr50 console to check and
+modify the capabilities, but CCD has to be [`Open`] to change the capabilities.
-#### CCD Password is Set
+Setting capabilities you want to use to [`Always`] will make them accessible
+even if CCD loses the [`Open`] state, which happens when Cr50 reboots or the
+device loses power.
-You can run ccd open with the password to open from the console.
+Basic CCD functionality is covered by `UartGscTxECRx`, `UartGscRxECTx`,
+`UartGscTxAPRx`, `UartGscRxAPTx`, [`FlashAP`], [`FlashEC`], [`OverrideWP`], and
+`GscFullConsole`.
```
-cr50 > ccd open $PASSWORD
+cr50 > ccd set $CAPABILITY $REQUIREMENT
```
-## Configure CCD
+### Examples
-Cr50 capabilities allow you to configure CCD to restrict or open the device as
-much as you want. You can use the `ccd` command to check and modify the
-capabilities. Cr50 has to be open to change the capabilities. Setting
-capabilities you want to use to Always will make them accessible even if cr50
-loses the open state. If you are using capabilities that may cause cr50 to
-reboot or may brick the device, you should set the capabilities needed to
-recover the device to Always or setup the capabilities so you can open cr50
-without booting the device.
-
-Basic ccd functionality is covered by UartGscTxECRx, UartGscRxECTx,
-UartGscTxAPRx, UartGscRxAPTx, FlashAP, FlashEC, OverrideWP, and GscFullConsole.
+#### EC Console
-You can go through the capability descriptions and figure out which ccd
-capabilities you want to use. After you figure that out you can modify the
-capabilities to Always be accessible.
-
-```
-cr50 > ccd set $CAP $REQ
-```
-
-For example if the EC console needs to be read-write even when Cr50 is locked
-set the capability to Always.
+If the EC console needs to be read-write even when CCD is [`Locked`] set the
+capability to [`Always`]:
```
cr50 > ccd set UartGscTxECRx Always
```
-If you want to restrict capabilities more you can set them to IfOpened. If you
-don’t want the AP/EC uart to be accessible at all when cr50 is locked, you can
-set them all to IfOpened.
+#### Restrict Consoles
+
+If you want to restrict capabilities more than [`Always`], you can set them to
+[`IfOpened`], which will make it so that it is only accessible when CCD is
+[`Open`]ed, not [`Lock`]ed:
-Restrict EC
+##### Restrict EC
```
cr50 > ccd set UartGscTxECRx IfOpened
cr50 > ccd set UartGscRxECTx IfOpened
```
-Restrict AP
+##### Restrict AP
```
cr50 > ccd set UartGscTxAPRx IfOpened
cr50 > ccd set UartGscRxAPTx IfOpened
```
+#### Most Accessible
+
If you want things as accessible as possible and want all capabilities to be
-Always, you can run
+[`Always`], you can run
```
cr50 > ccd reset factory
@@ -361,411 +320,152 @@ To reset capabilities to Default run
cr50 > ccd reset
```
-### Enable Open Without Requiring Device to Boot
-
-By default Cr50 requires enabling dev mode before you can open the device and
-the open command has to be sent from the AP. You can change the capabilities to
-remove these requirements if you think your development may prevent the device
-from booting. You can also set the ccd password to get around these
-requirements. These options offer different pros and cons. You can decide which
-is best for you.
-
-#### Set Capabilities
-
-After opening cr50, you can set these capabilities to reduce the restrictions
-required to open cr50.
-
-```
-cr50 > ccd set OpenFromUSB Always
-cr50 > ccd set OpenNoDevMode Always
-```
+## Flashing EC {#flashec}
-#### CCD Password
+Flashing the EC is restricted by the `FlashEC` capability.
-A ccd password can also be used to get around the open restrictions. The
-password will be required to reopen or unlock cr50, so keep track of the
-password. It can't be reset unless cr50 is open, so if you forget it, nothing
-can be done to reopen cr50.
-
-##### Set Password
-
-Run the `gsctool` command and enter the password when prompted. It will prompt
-for the password twice.
-
-```bash
-(chroot) $ gsctool -a -P
-```
-
-You can use the ccd command to check if the password is set.
-
-```
-cr50 > ccd
- ...
- Password: [none|set]
- ...
-```
-
-##### Clear Password
-
-You can clear the password by opening cr50 and then running the `gsctool`
-command again. When prompted for the password enter `clear:$PASSWORD` at both
-prompts.
-
-You can also use the cr50 `ccd reset` command when cr50 is open. This will clear
-the password and reset all ccd capabilities to default.
-
-##### Use Password
-
-After the password has been set you can use it to run ccd commands from the cr50
-console.
-
-```
-cr50 > ccd open $PASSWORD
-cr50 > ccd unlock $PASSWORD
-```
-
-You can use it from the AP shell
-
-```
-cr50 > gsctool -a -o
-cr50 > gsctool -a -u
-```
-
-enter the password when prompted
-
-# Using CCD
-
-## Rddkeepalive
-
-Cr50 only enables ccd when it detects a debug accessory is connected. It detects
-the cable based on the voltages on the CC lines. If you are flashing the EC and
-AP, these cc voltages may become unreliable for detecting a debug accessory. You
-can use a cr50 command to tell cr50 to ignore the voltages on these cc lines and
-just keep ccd enabled. There are many things that could interfere with rdd, so
-it’s probably best to run this before doing anything else using ccd.
-
-```
-cr50 > rddkeepalive enable
-```
-
-This command is useful for making sure ccd stays enabled during debugging. It
-will increase cr50 power a lot when the debug cable is disconnected. If you’re
-worried about that, disable rddkeepalive when you're not using ccd.
-
-```
-cr50 > rddkeepalive disable
-```
-
-## Consoles
-
-Cr50 presents 3 consoles through CCD. It has the AP, EC, and Cr50 console. The
-AP and EC consoles can be restricted using the 4 ccd uart capabilities
-**UartGscRxAPTx, UartGscTxAPRx, UartGscRxECTx, UartGscTxECRx**. The default
-setup is the AP is read write. The EC is read only. Cr50 console input/output
-can’t be suppressed.  You can only use the **GscFullConsole** capability to
-enable restricted console commands.
-
-Cr50 will create 3 /dev/ttyUSBX devices. They’re the cr50, AP, and EC console.
-The cr50 console normally has the lowest number. The AP and EC are the other
-two. You can figure out which one is which by pressing the power button or
-rebooting the device and looking at the uart output. If you have a bunch of
-devices, you can unplug suzyq and see which devices disappear to figure out the
-relevant ones.
-
-Servo can also figure this out for you. You can start servo like you normally do
-
-```bash
-(chroot) $ sudo servod -b $BOARD
-```
-
-After starting servo, you can use dut-control to get the consoles
-
-```bash
-(chroot) $ dut-control cr50_uart_pty ec_uart_pty cpu_uart_pty
-```
-
-## Flashing EC
-
-This is restricted by the **FlashEC** capability. This must be accessible to
-flash the EC.
-
-The steps to flash the EC differ a lot based on what board you’re using. You
-should stick to using `flash_ec` to handle flashing the ec, because the steps
-can get pretty complicated and are board specific.
-
-You will need to start servod then `flash_ec` will handle sending the correct
-cr50 console commands and updating the EC.
+The steps to flash the EC differ based on the board being used, but the
+[`flash_ec`] script will handle this for you.
```bash
(chroot) $ sudo servod -b $BOARD
(chroot) $ ~/trunk/src/platform/ec/util/flash_ec -i $IMAGE -b $BOARD
```
-## Flashing the AP
+## Flashing the AP {#flashap}
-This is restricted by the **FlashAP** capability. This must be accessible to
-flash the AP.
+*** note
+**WARNING**: Before attempting to flash the AP firmware, start with the
+[CCD Open] steps; if you flash broken firmware before opening CCD, you may make
+it impossible to restore your device to a working state.
+***
-Flashing the AP is standard across boards.
+Flashing the AP is restricted by the `FlashAP` capability.
```bash
(chroot) $ sudo flashrom -p raiden_debug_spi:target=AP -w $IMAGE
```
This default flashing command takes a very long time to complete, there are ways
-to speed up flashing process by cutting some corners, see the next section.
+to [speed up the flashing process] by cutting some corners.
-If you have a lot of ccd devices plugged in, you may want to use the cr50
-serialname. You can get this by running
+If you have many CCD devices connected, you may want to use the Cr50 serial
+number:
```bash
-(chroot) $ lsusb -vd 18d1:5014 | grep iSer
+(chroot) $ lsusb -vd 18d1:5014 | grep iSerial
```
-You can add the serialname to the flashrom command using
+You can then add the serial number to the [`flashrom`] command:
```bash
(chroot) $ sudo flashrom -p raiden_debug_spi:target=AP,serial=$SERIAL -w $IMAGE
```
-**If you don’t see cr50 print any messages when you’re running the flashrom
-command, you probably need to use the serialname.**
-
-### Speeding up flashing the AP
-
-The flashrom utility is designed without any consideration of the speed of
-access to the chip. While this is a reasonable omission when talking about
-inline programming, when the AP controls the SPI bus and can clock the bus at 50
-MHz, speed of access becomes a very annoying limitation when programming AP
-flash using Cr50, where SPI bus can not be clocked faster than 1.5 MHz.
-
-One of 'smart' tricks deployed by flashrom is reading the entire flash contents
-first, before programming, then erase and or program only flash pages which have
-to be modified. Some pages are probably still the same since the previous image
-was written, some pages could be programmed without erasing, etc.
-
-This trick is especially painful when flashing using Cr50, because reading the
-entire flash image clocking it at 1.5MHz alone takes a few minutes.
-
-After programming is completed, by default flashrom reads the flash contents
-back and compares them with the file used for programming. This second read also
-takes a few minutes, even if small portions of the chip were modified, the
-entire chip is read and compared.
-
-With these shortcomings in mind, a more efficient way of programming AP flash
-can be proposed. The flashrom utility was enhanced to prevent it from reading
-the contents of the flash before programming, and from reading the entire chip
-when verifying the write operation. It turns out it takes much less time to
-erase the entire flash chip first and then program only sections essential for
-the device booting in recovery mode. Once the device boots in recovery mode
-Chrome OS can be installed from a removable storage device, and then the entire
-flash can be programmed from the Chrome OS command line, with the AP clocking
-the bus at 50 MHz.
-
-Incidentally, any Chrome OS device AP firmware image is split into sections,
-which can be examined by running the command `dump_fmap <image file>`
-
-The `dump_fmap` utility finds in the image the section called `FMAP` and prints
-out its contents, which describes the layout of the entire flash image.
-
-Only a few sections are essential for maintaining the device identity and for
-booting the device in recovery mode. The `-i` command line option of `flashrom`
-allows the user to indicate which sections should be read/written.
-
-The below sequence of commands allows to quickly reprogram the AP flash:
-
-```bash
-# This will save device flash map and VPD sections in
-# /tmp/bios.essentials.bin. VPD sections contain information like device
-# firmware ID, WiFi calibration, enrollment status, etc. Use the below command
-# only if you need to preserve the DUT's identity, no need to run it in case
-# the DUT flash is not programmed at all, or you do not care about preserving
-# the device identity.
-sudo flashrom -p raiden_debug_spi:target=AP -i FMAP -i RO_VPD -i RW_VPD -r /tmp/bios.essentials.bin --fast-verify
+**If you don't see Cr50 print any messages when you're running the [`flashrom`]
+command and you have more than one Cr50 device connected to your workstation,
+you probably need to use the serial number.**
-# This command will erase the entire flash chip in one shot, the fastest
-# possible way to erase.
-sudo flashrom -p raiden_debug_spi:target=AP -E --do-not-diff
+### Special Cases {#flashap-special-cases}
-# This command will program essential flash sections necessary for the
-# Chrome OS device to boot in recovery mode. Note that the SI_ALL section is
-# not always present in the flash image, do not include it if it is not in
-# dump_fmap output.
-sudo flashrom -p raiden_debug_spi:target=AP -w image-atlas.bin -i FMAP -i WP_RO [-i SI_ALL] --do-not-diff --noverify
+Cr50 puts the device in reset to flash the AP. Due to hardware limitations Cr50
+may not be able to disable hardware write protect while the device is in reset.
+If you want to reflash the AP RO firmware using CCD and your board has issues
+disabling hardware write protect, you may need to also disable software write
+protect.
-# This command will restore the previously preserved VPD sections of the
-# flash, provided it was saved in the first step above.
-sudo flashrom -p raiden_debug_spi:target=AP -w /tmp/bios.essential.bin -i RO_VPD -i RW_VPD --do-not-diff --noverify
-```
+To determine if the board you are using has this issue:
-Once flash is programmed, the device can be booted in recovery mode and start
-Chrome OS from external storage, following the usual recovery procedure. Once
-Chrome OS is installed, AP flash can be updated to include the rest of the image
-by running flashrom or futility from the device bash prompt.
+1. Disable write protect using the Cr50 console command:
-## WP control
+ ```
+ cr50 > wp disable
+ ```
-This is restricted by the **OverrideWP** capability. If this capability is
-accessible, you can use the cr50 `wp` command. If it's not, you can only control
-write protect using battery presence.
+1. Check if hardware write protect disabled when the AP is off:
-### WP console command
+ ```bash
+ (chroot) $ sudo flashrom -p raiden_debug_spi:target=AP --wp-status
+ ```
-You can use the cr50 console command to change the write protect settings.
+1. If the last command shows that hardware write protect is still enabled when
+ the AP is off, then you need to disable software write protect:
-There are three write protect settings: `forced enabled`, `forced disabled`,
-`follow_batt_pres`.
+ ```bash
+ (chroot) $ flashrom -p host --wp-disable
+ ```
-* **`follow_batt_pres`** - DEFAULT SETTING - use battery presence to determine
- the write protect setting. If the battery is connected, enable write
- protect. If the battery is disconnected, disable write protect. If the board
- doesn’t have a battery, then normally a screw is used. If the screw is
- present, enable wp. If it’s not, disable wp.
+## Control Hardware Write Protect {#hw-wp}
-* **`enabled`** - enable write protect no matter the state of the battery.
- Protect things like the AP/EC flash and various other components that use
- this write protect signal
+Control of hardware write protect is restricted by the `OverrideWP` capability.
+When the capability is allowed, the hardware write protect setting can be
+controlled with the `wp` command in the Cr50 console. Otherwise, the hardware
+write protect is determined based on the presence of the battery.
-* **`disabled`** - write protect is deasserted no matter the state of the
- battery. You’ll be able to modify things like AP RO
+Hardware Write Protect Setting | Battery State | Hardware Write Protect State
+------------------------------ | ------------------------------ | ----------------------------
+`follow_batt_pres` | Connected | Enabled
+`follow_batt_pres` | Disconnected | Disabled
+`follow_batt_pres` | N/A (Chromebox has no battery) | Write Protect Screw means Enabled
+`enabled` | Any | Enabled
+`disabled` | Any | Disabled
-You can set these from the cr50 console
+### Write Protect Commands
```
cr50 > wp [enable|disable|follow_batt_pres]
```
-This setting will persist until it is cleared using the wp command or until cr50
-reboots/loses power. After these resets, cr50 will default to the `atboot`
-setting. The default setting is `follow_batt_pres`, so cr50 will go back to
-following battery presence after reboot unless the `atboot` setting has been
-overridden.
+There are two write protect settings: the current setting and the `atboot`
+setting.
-Using the `atboot` arg will update the current and atboot wp state. If the
-`atboot` arg is given to the wp command, then the setting will persist until it
-is cleared by the wp command. It won’t be reset by anything else, so if you only
-want to disable/enable write protect for a short time, make sure atboot is set
-to `follow_batt_pres`. If you want to permanently disable or enable write
-protect and want to ignore the battery, this is a good setting to update.
+The `wp` command adjusts the current write protect setting that will last until
+Cr50 reboots or loses power. Note that Cr50 does not reboot when the rest of the
+system reboots. It will only reboot in the cases where the firmware is being
+updated, it crashes, the battery completely drains, the battery is removed, or
+power is otherwise lost.
-```
-cr50 > wp [enable|disable|follow_batt_pres]
-```
+The `atboot` setting is the state of the write protect when Cr50 boots; it
+defaults to `follow_batt_pres`.
-You can use the wp command to get the write protect state even if the capability
-is restricted.
+To change the `atboot` setting, add the `atboot` arg to the `wp` command:
```
-cr50 > wp
-
- Flash WP: [forced ]enabled|disabled
-  atboot: forced enabled | force disabled | follow_batt_pres
+cr50 > wp atboot [enable|disable|follow_batt_pres]
```
-`gsctool` also supports getting the write protect state
+You can query the write protect state with `gsctool`:
```bash
-(dut) $ gsctool -a -W
-```
-
-The output will show the current and `atboot` setting.
+(dut) $ gsctool -a -w
-The current wp setting will not explicitly show that write protect is currently
-following battery presence. You have to get this by checking if the wp state is
-‘forced’ enabled/disabled. Forced means write protect is being overridden by the
-console command. If it just shows the state without forced, write protect is
-following battery presence.
-
-The `atboot` setting shows what the wp state will reset to after reboot.
-
-### Battery Presence
-
-If the OverrideWP command isn’t accessible, you can use battery presence to
-change the wp state as long as the wp setting is still `follow_batt_pres`.
-
-* wp disable - disconnect the battery
-
-* wp enable - connect the battery
-
-If the wp setting has been overridden by ccd, this won’t work until the current
-wp setting is reset to `follow_batt_pres`
+...
+Flash WP: forced disabled <-- Current hardware write protect state
+ at boot: forced disabled <-- "atboot" hardware write protect state
```
-cr50 > wp follow_batt_pres atboot
-```
-
-### HW WP Issues
-
-#### Chromeboxes
-
-Chromeboxes do not have batteries, so cr50 can't use battery presence for write
-protect. They use a write protect screw. You need to remove the write protect
-screw to disable write protect if cr50 is set to `follow_batt_pres`.
-#### Bob
-
-Bob's have a write protect screw in addition to battery presence. The write
-protect screw will force enable write protect until it's removed. If cr50 is set
-to `follow_batt_pres`, you need to remove the write protect screw and disconnect
-the battery to disable write protect. If you run `wp disable`, you will also
-need to remove the screw.
-
-#### AP Off
-
-Cr50 puts the device in reset to flash the AP. Due to hardware limitations Cr50
-may not be able to disable write protect while the device is in reset. If you
-want to reflash RO firmware using CCD and your board has issues disabling HW WP,
-you may need to disable SW write protect.
-
-Check if your board has this issue
-
-1. Disable write protect using the cr50 console command
-
-1. Check it's still disabled when the AP is off. This command should show write
- protect is disabled. If it shows it's enabled, then cr50 can't disable WP
- when the AP is off. You should disable SW WP to flash RO firmware using ccd.
-
- ```bash
- (chroot) $ sudo flashrom -p raiden_debug_spi:target=AP --wp-status
- ```
-
-Disable SW WP if the ccd flashrom command doesn't show write protect disabled.
-
-```bash
-(chroot) $ flashrom -p host --wp-disable
-```
-
-# CCD as a Servo replacement
-
-Once cr50 is open and all capabilities have been set to Always, cr50 should be
-able to be used as a servo replacement. It has all of the capabilities servo
-does and support has been added to hdctools to convert servo controls to cr50
-and ec console commands.
-
-If you start `servod` and select the ccd device, you should be able to use servo
-`dut-control` commands normally.
-
-```bash
-(chroot) $ sudo servod -b $BOARD
-```
+`gsctool -a -w` Status | Hardware Write Protect State
+---------------------- | ------------------------------------
+`forced disabled` | Disabled
+`forced enabled` | Enabled
+`enabled` | Enabled, following battery presence
+`disabled` | Disabled, following battery presence
-If cr50 reboots or usb disconnects for some reason, servod will lose the
-connection to the cr50 usb. Support has just been added to hdctools to
-reinitialize all of the servo ccd interfaces, so things should come back up
-after the disconnect, but it might still have bugs.
+### Special Case Devices
-Servo can take care of a lot of the less intuitive things for you like during
-init it will send `rddkeepalive enable`. It will also find the AP, EC, and Cr50
-uart. Servod knows how to interact with the i2c endpoint, so you can use servod
-to read power from the INAs if they’re populated.
+Bob devices have a write protect screw in addition to battery presence. The
+write protect screw will force enable write protect until it's removed. If Cr50
+is set to `follow_batt_pres`, you need to remove the write protect screw and
+disconnect the battery to disable write protect. If you run `wp disable`, you
+will also need to remove the screw.
-Suzyq doesn’t have all of the necessary things to replace servo for FAFT, but
-you should be able to use it for normal debugging functionality. You will need a
-type c servo v4 for ccd if you need to run FAFT.
+If you are attempting to flash the AP, see the [Flashing the AP Special Cases]
+section for additional steps you may have to take to disable write protection.
-# UART Rescue mode
+## UART Rescue mode
-## Overview
+### Overview
UART Rescue Mode is a feature of the Cr50 RO firmware that supports programming
the RW firmware using only the UART interface. This is used to recover a bad RW
@@ -778,24 +478,25 @@ UART rescue works on all existing devices, all it requires is that Cr50 console
is mapped to a `/dev/xxx` device on the workstation (the same device used to
attach a terminal to the console).
-Rescue works as follows: when the RO starts, it prints out on the console a
-certain string and momentarily waits for the host to send a sync symbol, to
-indicate that an alternative RW will have to be loaded over UART. The RO also
-enters this mode if there is no valid RW to run.
+Rescue works as follows: when the RO starts, after printing the regular banner
+on the console it prints a magic string to the console and momentarily waits for
+the host to send a sync symbol, to indicate that an alternative RW will have to
+be loaded over UART. The RO also enters this mode if there is no valid RW to
+run.
When rescue mode is triggered, the RO is expecting the host to transfer a single
RW image in hex format.
-## Install the cr50-rescue utility
+### Install the cr50-rescue utility
-The `cr50-rescue` utility is used to flash a given firmware to cr50 using rescue
+The `cr50-rescue` utility is used to flash a given firmware to Cr50 using rescue
mode. This tool must be installed inside the chroot.
```bash
(chroot) $ sudo emerge cr50-utils
```
-## Preparing an RW image
+### Preparing an RW image
To prepare the signed hex RW image, fetch a released image from Google storage,
which can be found by running:
@@ -808,7 +509,7 @@ which can be found by running:
image you want to use for rescue to your workstation and extract cr50.bin.prod
from the tarball.
-The latest cr50 images can be found in the [chromeos-cr50 ebuild]. Generally,
+The latest Cr50 images can be found in the [chromeos-cr50 ebuild]. Generally,
you should always use the PROD_IMAGE indicated in that file. Once rescued, the
user can update to the PREPVT image later if needed.
@@ -822,23 +523,24 @@ objcopy -I binary -O ihex --change-addresses 0x44000 cr50.rw.bin cr50.rw.hex
then you can use `cr50.rw.hex` as the image passed to `cr50-rescue`.
-## Programming the RW image with rescue mode
+### Programming the RW image with rescue mode
With servo_micro (or servo_v2 reworked for connecting to Cr50 console), run
-servod and disable cr50 ec3po and uart timestamp:
+[`servod`] and disable Cr50 ec3po and UART timestamp:
```bash
(chroot) $ dut-control cr50_uart_timestamp:off dut-control cr50_ec3po_interp_connect:off
```
-Get a raw cr50 uart device path and use it for cr50-rescue argument `-d` below.
+Get a raw Cr50 UART device path and use it for `cr50-rescue` argument `-d`
+below.
```bash
(chroot) $ dut-control raw_cr50_uart_pty
```
-Prior to running `cr50-rescue`, the terminal from the cr50 console UART must be
-disconnected, and cr50 must be unpowered-- the system needs to have AC power and
+Prior to running `cr50-rescue`, the terminal from the Cr50 console UART must be
+disconnected, and Cr50 must be unpowered-- the system needs to have AC power and
battery disconnected.
After ensuring those steps, the rescue command may be run as follows:
@@ -848,11 +550,11 @@ After ensuring those steps, the rescue command may be run as follows:
```
After starting the command, provide power to the board and rescue mode will
-start automatically. After flashing successfully (see sample output below), cr50
+start automatically. After flashing successfully (see sample output below), Cr50
must be unpowered again, by disconnecting AC power and battery.
Note that `<cr50 console UART tty>` above has to be a direct FTDI interface,
-`pty` devices created by servod do not work for this purpose. Use either
+`pty` devices created by [`servod`] do not work for this purpose. Use either
servo-micro or a USB/UART cable. Note that multifunctional *SPI-UART/FTDI/USB
cables might not work*, as they impose a significant delay in the UART stream,
which makes the synchronization described below impossible.
@@ -863,7 +565,7 @@ the target output, at this point the utility intercepts the boot process and the
target proceeds to receiving the new RW image and saving it into flash. Note the
currently present RW and RW_B images will be wiped out first.
-### Sample output
+#### Sample output
```bash
(chroot) $ cr50-rescue -v -i cr50.3.24.rw.hex -d /dev/pts/0
@@ -891,6 +593,241 @@ retry|0
oops?|0.1.2.3.4.5.6.7.8.9.10.11.12.13.14.15.16.17.18.19.20.21.22.23.24.25.26.27.28.29.30.31.32.33.34.35.36.37.38.39.40.41.42.43.44.45.46.47.48.49.50.51.52.53.54.55.56.57.58.59.60.61.62.63.64.65.66.67.68.69.70.71.72.73.74.75.76.77.78.79.80.81.82.83.84.85.86.87.88.89.90.91.92.93.94.95.96.97.98.99.100.101.102.103.104.105.106.107.108.109.110.111.112.113.114.115.116.117.118.119.120.121.122.123.124.125.126.127.128.129.130.131.132.133.134.135.136.137.138.139.140.141.142.143.144.145.146.147.148.149.150.151.152.153.154.155.156.157.158.159.160.161.162.163.164.165.166.167.168.169.170.171.172.173.174.175.176.177.178.179.180.181.182.183.184.185.186.187.188.189.190.191.192.193.194.195.196.197.198.199.200.201.202.203.204.205.206.207.208.209.210.211.212.213.214.215.216.217.218.219.220.221.222.223.224.225.done!
```
+## CCD Open Without Booting the Device {#ccd-open-no-boot}
+
+If you can’t boot your device, you won’t be able to enable [Developer Mode] to
+send the open command from the AP. If you have enabled CCD on the device before,
+Cr50 may be configured in a way that you can still open Cr50.
+
+### Option 1: Remove the battery
+
+If you can remove the battery, you can bypass the [Developer Mode] requirements.
+`ccd open` is allowed from the Cr50 console if the Chrome OS Firmware Management
+Parameters (`FWMP`) do not disable CCD and the battery is disconnected. This is
+the most universal method and will work even if you haven’t enabled CCD before.
+
+1. Disconnect the battery
+
+1. Send `ccd open` from the Cr50 console.
+
+### Option 2: "OpenNoDevMode" and "OpenFromUSB" are set to Always
+
+If "OpenNoDevMode" and "OpenFromUSB" are set to Always, you will be able to open
+Cr50 from the Cr50 console without enabling [Developer Mode]:
+
+```
+cr50 > ccd open
+```
+
+You will still need physical presence (i.e., press the power button) unless
+`testlab` mode is also enabled:
+
+```
+cr50 > ccd testlab
+ CCD test lab mode enabled
+```
+
+#### Enabling
+
+If CCD is [`Open`], you can enable these settings with:
+
+```
+cr50 > ccd set OpenFromUSB Always
+cr50 > ccd set OpenNoDevMode Always
+```
+
+### Option 3: CCD Password is Set
+
+If the CCD password is set, you can open from the Cr50 console without
+[Developer Mode].
+
+```
+cr50 > ccd open $PASSWORD
+cr50 > ccd unlock $PASSWORD
+```
+
+Alternatively, you can use `gsctool`, entering the password when prompted:
+
+```
+(dut) $ gsctool -a -o
+(dut) $ gsctool -a -u
+```
+
+#### Enabling
+
+When CCD is [`Open`], run the `gsctool` command and enter the password when
+prompted.
+
+```bash
+(chroot) $ gsctool -a -P
+```
+
+You can use the CCD command on the Cr50 console to check if the password is set.
+
+```
+cr50 > ccd
+ ...
+ Password: [none|set]
+ ...
+```
+
+#### Disabling
+
+When CCD is [`Open`], you can use `gsctool` to clear the password:
+
+```bash
+(dut) $ gsctool -a -P clear:$PASSWORD
+```
+
+Alternatively, you can use the Cr50 console to clear the password and reset CCD
+capabilities to their default values:
+
+```
+cr50 > ccd reset
+```
+
+## Troubleshooting
+
+### rddkeepalive
+
+Cr50 only enables CCD when it detects a debug accessory is connected (e.g.,
+[Suzy-Q] or [Type-C Servo v4]). It detects the cable based on the voltages on
+the CC lines. If you are flashing the EC and AP or working with unstable
+hardware, these CC voltages may become unreliable for detecting a debug
+accessory.
+
+To work around this, you can force Cr50 to always assume that a debug cable is
+detected:
+
+```
+cr50 > rddkeepalive enable
+```
+
+*** note
+**NOTE**: Enabling `rddkeepalive` does increase power consumption.
+***
+
+To disable:
+
+```
+cr50 > rddkeepalive disable
+```
+
+### Updating Cr50 {#updating-cr50}
+
+Production (`MP`) versions of Cr50 firmware use a [minor version][semver] of
+`3`: `0.3.x`. Production firmware versions `0.3.9` or newer support CCD.
+
+Development (`PrePVT`) versions of Cr50 firmware use a minor version of `4`:
+`0.4.x`. Development firmware versions `0.4.9` or newer support CCD.
+
+There aren't many differences between the MP and PrePVT versions of images, but
+it is a little easier to CCD [`Open`] PrePVT images. You can't run PrePVT images
+on MP devices, so if you're trying to update to PrePVT and it fails try using
+the MP image.
+
+1. Flash a test image newer than M66.
+
+1. Enable [Developer Mode] and connect a debug cable ([`Suzy-Q`] or [`Type-C
+ Servo v4`]).
+
+1. Check the running Cr50 version with `gsctool`:
+
+```bash
+(dut) $ sudo gsctool -a -f
+
+...
+RW 0.4.26 <-- The "RW" version is the one to check
+```
+
+1. Update Cr50 using the firmware in the OS image:
+
+*Production (MP) image*:
+
+```bash
+(dut) $ sudo gsctool -a /opt/google/cr50/firmware/cr50.bin.prod
+```
+
+*Development (PrePVT) image*:
+
+```bash
+(dut) $ sudo gsctool -a /opt/google/cr50/firmware/cr50.bin.prepvt
+```
+
+1. Check the Cr50 version again to make sure it's either `0.3.X` or `0.4.X`.
+
+### Speed up Flashing the AP {#speed-up-ap-flash}
+
+In the [default AP flashing steps][flashap] [`flashrom`] reads the entire flash
+contents and only erases and programs the pages that have to be modified.
+However, when Cr50 controls the SPI bus, it can only run at 1.5 MHz, versus the
+50 MHz that the AP normally runs it at.
+
+We can take advantage of the fact that Chrome OS device AP firmware is split
+into sections, only a few of which are essential for maintaining the device
+identity and for booting the device in recovery mode to program faster by only
+reading and writing sections we care about:
+
+```bash
+# This will save device flash map and VPD sections in
+# /tmp/bios.essentials.bin. VPD sections contain information like device
+# firmware ID, WiFi calibration, enrollment status, etc. Use the below command
+# only if you need to preserve the DUT's identity, no need to run it in case
+# the DUT flash is not programmed at all, or you do not care about preserving
+# the device identity.
+sudo flashrom -p raiden_debug_spi:target=AP -i FMAP -i RO_VPD -i RW_VPD -r /tmp/bios.essentials.bin --fast-verify
+
+# This command will erase the entire flash chip in one shot, the fastest
+# possible way to erase.
+sudo flashrom -p raiden_debug_spi:target=AP -E --do-not-diff
+
+# This command will program essential flash sections necessary for the
+# Chrome OS device to boot in recovery mode. Note that the SI_ALL section is
+# not always present in the flash image, do not include it if it is not in
+# dump_fmap output.
+sudo flashrom -p raiden_debug_spi:target=AP -w image-atlas.bin -i FMAP -i WP_RO [-i SI_ALL] --do-not-diff --noverify
+
+# This command will restore the previously preserved VPD sections of the
+# flash, provided it was saved in the first step above.
+sudo flashrom -p raiden_debug_spi:target=AP -w /tmp/bios.essential.bin -i RO_VPD -i RW_VPD --do-not-diff --noverify
+```
+
+Once flash is programmed, the device can be booted in recovery mode and start
+Chrome OS from external storage, following the usual recovery procedure. Once
+Chrome OS is installed, AP flash can be updated to include the rest of the image
+by running [`flashrom`] or `futility` from the device bash prompt.
+
+[Case Closed Debugging]: ./case_closed_debugging.md
[chromeos-cr50 ebuild]: https://chromium.googlesource.com/chromiumos/overlays/chromiumos-overlay/+/refs/heads/master/chromeos-base/chromeos-cr50/chromeos-cr50-0.0.1.ebuild
[Developer Mode]: https://chromium.googlesource.com/chromiumos/docs/+/master/developer_mode.md#dev-mode
[Recovery Mode]: https://chromium.googlesource.com/chromiumos/docs/+/master/debug_buttons.md
+[Servo]: https://chromium.googlesource.com/chromiumos/third_party/hdctools/+/master/docs/servo.md
+[`servod`]: https://chromium.googlesource.com/chromiumos/third_party/hdctools/+/master/docs/servo.md
+[Type-C Servo v4]: https://chromium.googlesource.com/chromiumos/third_party/hdctools/+/master/docs/servo_v4.md
+[update servo v4]: https://chromium.googlesource.com/chromiumos/third_party/hdctools/+/master/docs/servo_v4.md#updating-firmware
+[Suzy-Q]: https://chromium.googlesource.com/chromiumos/third_party/hdctools/+/master/docs/ccd.md#SuzyQ-SuzyQable
+[`hdctools`]: https://chromium.googlesource.com/chromiumos/third_party/hdctools/+/refs/heads/master/README.md
+[`FlashAP`]: #flashap
+[flashing the AP firmware]: #flashap
+[flashap]: #flashap
+[Flashing the AP Special Cases]: #flashap-special-cases
+[`FlashEC`]: #flashec
+[flashing the EC firmware]: #flashec
+[`OverrideWP`]: #hw-wp
+[`Always`]: #cap-priv
+[`IfOpened`]: #cap-priv
+[`Open`]: #cap-priv
+[`Locked`]: #cap-priv
+[`Unlocked`]: #cap-priv
+[Updating Cr50]: #updating-cr50
+[CCD Open Without Booting the Device]: #ccd-open-no-boot
+[cap]: #cap
+[consoles]: #consoles
+[hw-wp]: #hw-wp
+[`flash_ec`]: https://chromium.googlesource.com/chromiumos/platform/ec/+/master/util/flash_ec
+[CCD Open]: #ccd-open
+[`flashrom`]: https://chromium.googlesource.com/chromiumos/third_party/flashrom/+/master/README.chromiumos
+[speed up the flashing process]: #speed-up-ap-flash
+[this bug]: https://issuetracker.google.com/149420712
+[semver]: https://semver.org/
+[`usb_console`]: https://chromium.googlesource.com/chromiumos/platform/ec/+/master/extra/usb_serial/console.py