1 /* Copyright 2019 The ChromiumOS Authors 2 * Use of this source code is governed by a BSD-style license that can be 3 * found in the LICENSE file. 4 * 5 * Utilities for firmware updater. 6 */ 7 8 #ifndef VBOOT_REFERENCE_FUTILITY_UPDATER_UTILS_H_ 9 #define VBOOT_REFERENCE_FUTILITY_UPDATER_UTILS_H_ 10 11 #include <stdbool.h> 12 #include <stdio.h> 13 #include "fmap.h" 14 15 #define ASPRINTF(strp, ...) do { if (asprintf(strp, __VA_ARGS__) >= 0) break; \ 16 ERROR("Failed to allocate memory, abort.\n"); exit(1); } while (0) 17 18 /* Structure(s) declared in updater_archive */ 19 struct u_archive; 20 21 /* Firmware slots */ 22 static const char * const FWACT_A = "A", 23 * const FWACT_B = "B"; 24 25 enum active_slot { 26 SLOT_UNKNOWN = -1, 27 SLOT_A = 0, 28 SLOT_B, 29 }; 30 31 /* Utilities for managing temporary files. */ 32 struct tempfile { 33 char *filepath; 34 struct tempfile *next; 35 }; 36 37 /* 38 * Create a new temporary file. 39 * 40 * The parameter head refers to a linked list dummy head. 41 * Returns the path of new file, or NULL on failure. 42 */ 43 const char *create_temp_file(struct tempfile *head); 44 45 /* 46 * Remove all files created by create_temp_file(). 47 * 48 * The parameter head refers to the dummy head of linked list. 49 * This is intended to be called only once at end of program execution. 50 */ 51 void remove_all_temp_files(struct tempfile *head); 52 53 /* Include definition of 'struct firmware_image;' */ 54 #include "flashrom.h" 55 56 enum { 57 IMAGE_LOAD_SUCCESS = 0, 58 IMAGE_READ_FAILURE = -1, 59 IMAGE_PARSE_FAILURE = -2, 60 }; 61 62 /* 63 * Loads a firmware image from file. 64 * If archive is provided and file_name is a relative path, read the file from 65 * archive. 66 * Returns IMAGE_LOAD_SUCCESS on success, IMAGE_READ_FAILURE on file I/O 67 * failure, or IMAGE_PARSE_FAILURE for non-vboot images. 68 */ 69 int load_firmware_image(struct firmware_image *image, const char *file_name, 70 struct u_archive *archive); 71 72 /* Structure(s) declared in updater.h */ 73 struct updater_config; 74 75 /* 76 * Loads the active system firmware image (usually from SPI flash chip). 77 * Returns 0 if success. Returns IMAGE_PARSE_FAILURE for non-vboot images. 78 * Returns other values for error. 79 */ 80 int load_system_firmware(struct updater_config *cfg, 81 struct firmware_image *image); 82 83 /* Frees the allocated resource from a firmware image object. */ 84 void free_firmware_image(struct firmware_image *image); 85 86 /* Preserves meta data and reloads image contents from given file path. */ 87 int reload_firmware_image(const char *file_path, struct firmware_image *image); 88 89 /* Checks the consistency of RW A and B firmware versions. */ 90 void check_firmware_versions(const struct firmware_image *image); 91 92 /* 93 * Generates a temporary file for snapshot of firmware image contents. 94 * 95 * Returns a file path if success, otherwise NULL. 96 */ 97 const char *get_firmware_image_temp_file(const struct firmware_image *image, 98 struct tempfile *tempfiles); 99 100 /* 101 * Writes sections from a given firmware image to the system firmware. 102 * regions_len should be zero for writing the whole image; otherwise, regions 103 * should contain a list of FMAP section names of at least regions_len size. 104 * Returns 0 if success, non-zero if error. 105 */ 106 int write_system_firmware(struct updater_config *cfg, 107 const struct firmware_image *image, 108 const char *const regions[], size_t regions_len); 109 110 struct firmware_section { 111 uint8_t *data; 112 size_t size; 113 }; 114 115 /* 116 * Returns true if the given FMAP section exists in the firmware image. 117 */ 118 int firmware_section_exists(const struct firmware_image *image, 119 const char *section_name); 120 121 /* 122 * Finds a firmware section by given name in the firmware image. 123 * If successful, return zero and *section argument contains the address and 124 * size of the section; otherwise failure. 125 */ 126 int find_firmware_section(struct firmware_section *section, 127 const struct firmware_image *image, 128 const char *section_name); 129 130 /* 131 * Preserves (copies) the given section (by name) from image_from to image_to. 132 * The offset may be different, and the section data will be directly copied. 133 * If the section does not exist on either images, return as failure. 134 * If the source section is larger, contents on destination be truncated. 135 * If the source section is smaller, the remaining area is not modified. 136 * Returns 0 if success, non-zero if error. 137 */ 138 int preserve_firmware_section(const struct firmware_image *image_from, 139 struct firmware_image *image_to, 140 const char *section_name); 141 142 /* 143 * Overwrite the given offset of a section in the firmware image with the 144 * given values. 145 * Returns 0 on success, otherwise failure. 146 */ 147 int overwrite_section(struct firmware_image *image, 148 const char *fmap_section, size_t offset, 149 size_t size, const uint8_t *new_values); 150 151 /* 152 * Returns rootkey hash of firmware image, or NULL on failure. 153 */ 154 const char *get_firmware_rootkey_hash(const struct firmware_image *image); 155 156 /* 157 * Finds the GBB (Google Binary Block) header on a given firmware image. 158 * Returns a pointer to valid GBB header, or NULL on not found. 159 */ 160 struct vb2_gbb_header; 161 const struct vb2_gbb_header *find_gbb(const struct firmware_image *image); 162 163 /* 164 * Strips a string (usually from shell execution output) by removing all the 165 * trailing characters in pattern. If pattern is NULL, match by space type 166 * characters (space, new line, tab, ... etc). 167 */ 168 void strip_string(char *s, const char *pattern); 169 170 /* 171 * Saves everything from stdin to given output file. 172 * Returns 0 on success, otherwise failure. 173 */ 174 int save_file_from_stdin(const char *output); 175 176 /* 177 * Returns true if the AP write protection is enabled on current system. 178 */ 179 bool is_ap_write_protection_enabled(struct updater_config *cfg); 180 181 /* 182 * Returns true if the EC write protection is enabled on current system. 183 */ 184 bool is_ec_write_protection_enabled(struct updater_config *cfg); 185 186 /* 187 * Executes a command on current host and returns stripped command output. 188 * If the command has failed (exit code is not zero), returns an empty string. 189 * The caller is responsible for releasing the returned string. 190 */ 191 char *host_shell(const char *command); 192 193 /* The environment variable name for setting servod port. */ 194 #define ENV_SERVOD_PORT "SERVOD_PORT" 195 196 /* The environment variable name for setting servod name. */ 197 #define ENV_SERVOD_NAME "SERVOD_NAME" 198 199 /* 200 * Helper function to detect type of Servo board attached to host. 201 * Returns a string as programmer parameter on success, otherwise NULL. 202 */ 203 char *host_detect_servo(const char **prepare_ctrl_name); 204 205 /* 206 * Makes a dut-control request for control_name. 207 * Sets control_name to "on" if on is non zero, else "off". 208 * Does not check for failure. 209 */ 210 void prepare_servo_control(const char *control_name, bool on); 211 212 /* DUT related functions (implementations in updater_dut.c) */ 213 214 struct dut_property { 215 int (*getter)(struct updater_config *cfg); 216 int value; 217 int initialized; 218 }; 219 220 enum dut_property_type { 221 DUT_PROP_MAINFW_ACT, 222 DUT_PROP_TPM_FWVER, 223 DUT_PROP_PLATFORM_VER, 224 DUT_PROP_WP_HW, 225 DUT_PROP_WP_SW_AP, 226 DUT_PROP_WP_SW_EC, 227 DUT_PROP_MAX 228 }; 229 230 /* Helper function to initialize DUT properties. */ 231 void dut_init_properties(struct dut_property *props, int num); 232 233 /* Gets the DUT system property by given type. Returns the property value. */ 234 int dut_get_property(enum dut_property_type property_type, 235 struct updater_config *cfg); 236 237 int dut_set_property_string(const char *key, const char *value, 238 struct updater_config *cfg); 239 int dut_get_property_string(const char *key, char *dest, size_t size, 240 struct updater_config *cfg); 241 int dut_set_property_int(const char *key, const int value, 242 struct updater_config *cfg); 243 int dut_get_property_int(const char *key, struct updater_config *cfg); 244 245 /* Gets the 'firmware manifest key' on the DUT. */ 246 int dut_get_manifest_key(char **manifest_key_out, struct updater_config *cfg); 247 248 #endif /* VBOOT_REFERENCE_FUTILITY_UPDATER_UTILS_H_ */ 249