1# In-Band Update of BMC Firmware using USB 2 3Author: George Liu <liuxiwei!> 4 5Created: 2021-10-12 6 7## Problem Description 8 9When Redfish or scp cannot be used, BMC needs a new mechanism for images to get 10into the machine. 11 12## Background and References 13 14The openbmc project currently has a [phosphor-software-manager][1] repository. 15In order to perform an update, need first to bring the image into the BMC 16directory (/tmp/images). However, only TFTP and HTTP are currently supported, 17and USB is not yet supported. 18 19The intent of this new application design is to enable the USB driver of BMC to 20enter the new image into BMC. 21 22## Requirements 23 24The following statements are reflective of the initial requirements. 25 26- Monitor whether the USB key is inserted. 27- The first tar file found in the sorted list of files on the USB device is 28 copied to `/tmp/images`. 29- Manually trigger firmware upgrade. 30- Disable automatic reboot the BMC firmware after upgrade is complete to prevent 31 a potential loop in the event of a key inserted. 32- This mechanism attempts to maintain security, for example this feature is 33 disabled by default or can be enabled or disabled via Redfish. 34 35## Proposed Design 36 37The new code would be part of the phosphor-software-manager repository(eg: 38phosphor-usb-code-update). The design process is as follows: 39 40- Define a macro switch (`usb-code-update`) in [phosphor-software-manager][1] 41 repository to identify whether to enable the USB Code Update function, which 42 is _enabled_ by default. 43- If `usb-code-update` enabled, install the udev rules file to 44 `/lib/udev/rules.d` during compilation. 45- Once the udev rules are met, the systemd service is directly triggered and 46 start the phosphor-usb-code-update daemon. 47- This daemon verifies the `/run/media/usb/sda1` directory and copies the first 48 `.tar` file in the directory to `/tmp/images` and starts verification. 49- Set ApplyTime to OnReset so that the proposed usb code update app does not 50 reboot the BMC after activation. 51- Set RequestedActivation to Active, follow the updated status, start to update 52 the firmware, and restart the BMC after completion. 53- Exit the phosphor-usb-code-update daemon. 54 55## Pseudocode 56 57The udev rules files for example: 58 59``` 60SUBSYSTEM=="block", ACTION=="add", ENV{ID_USB_DRIVER}=="usb-storage", ENV{DEVTYPE}=="partition", ENV{SYSTEMD_WANTS}="usb-code-update@%k", TAG+="systemd" 61``` 62 63## Security 64 65- It is recommended to run a local CI run and analyze & avoid potential 66 vulnerabilities via cppcheck. 67- Assuming that the USB drive has a physical security vulnerability (such as 68 memory overflow, etc.), should disable "USB code update" via Redfish. After 69 the vulnerability is fixed, enable "USB code update" again via Redfish. 70 71## Alternatives Considered 72 73If the OS fails to boot due to an error, so the firmware update cannot be done 74through the OS, or the network fails, and the update cannot be done through 75Redfish or scp, the server support staff can only uninstall the flash chip and 76re-flashing, this is not Reasonably, service support should have local access to 77the machine and update the system to a working firmware level. 78 79## Impacts 80 81This impacts security because it can copy files to the BMC via an external USB 82key. There is no expected performance impact since the process just copies files 83during runtime and exits automatically after completion. 84 85## Testing 86 87- When the USB code update is disabled, the service will return directly without 88 any update. 89- Manually insert the USB key with the firmware upgrade package, and check 90 whether the upgrade file is correct through the log. 91- Simulate `dev/sda1` on qemu with some test scripts and start the service(eg: 92 `systemcl start usb-code-update@sda1.service`) 93- Verify that the ApplyTime attribute value is set to OnRest. 94- Verify that the RequestedActivation property value is set to Active. 95- Verify that the firmware update was successful. 96 97[1]: https://github.com/openbmc/phosphor-bmc-code-mgmt 98