blob: 40ec17b3f6351eb5fb0bf0d23e50e9f31065f2d2 [file] [log] [blame]
#!/bin/sh
# Copyright 2016 The Chromium OS Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
. /usr/share/misc/shflags
. /opt/google/touch/scripts/chromeos-touch-common.sh
DEFINE_boolean 'recovery' ${FLAGS_FALSE} "Recovery. Allows for rollback" 'r'
DEFINE_string 'device' '' "device_name" 'd'
FW_LINK_BASE="wacom_firmware.hex"
WACOMFLASH="/usr/sbin/wacom_flash"
GET_ACTIVE_FIRMVER="-a"
# Parse command line.
FLAGS "$@" || exit 1
eval set -- "${FLAGS_ARGV}"
update_firmware() {
# Actually trigger a firmware update by running the Wacom update tool
# in minijail to limit the syscalls it can access.
local fw_link="$1"
local cmd_log=""
cmd_log="$(
minijail0 -S /opt/google/touch/policies/wacom_flash.update.policy \
"${WACOMFLASH}" "${fw_link}" ${FLAGS_recovery} ${FLAGS_device} 2>&1
)"
if [ "$?" -ne 0 ]; then
die "Error updating touch firmware: ${cmd_log}"
fi
}
get_fw_version_from_disk() {
# The on-disk FW version is determined by reading the filename which
# is in the format "wacom_FWVERSION.hex". We follow the fw's link
# to the actual file then strip away everything in the FW's filename
# but the FW version.
local fw_link="$1"
local fw_filepath=""
local fw_filename=""
local fw_ver=""
if [ ! -L "${fw_link}" ]; then
return
fi
fw_filepath="$(readlink -f "${fw_link}")"
if [ ! -e "${fw_filepath}" ]; then
return
fi
fw_filename="$(basename "${fw_filepath}")"
fw_ver="${fw_filename#*_}"
fw_ver="${fw_ver%.*}"
echo "${fw_ver}"
}
get_active_fw_version() {
# Query the touchscreen and see what the current FW version it's running.
local active_fw_ver=""
active_fw_ver="$(
minijail0 -S /opt/google/touch/policies/wacom_flash.query.policy \
"${WACOMFLASH}" "dummy_unused_argument" "${GET_ACTIVE_FIRMVER}" \
"${FLAGS_device}"
)"
if [ "$?" -eq 0 ]; then
echo "${active_fw_ver}"
fi
}
i2c_chardev_present() {
# This function tests to see if there are any i2c char devices on the system.
# It returns 0 iff /dev/i2c-* matches at least one file.
local f=""
for f in /dev/i2c-*; do
if [ -e "${f}" ]; then
return 0
fi
done
return 1
}
main() {
# Check to make sure the required drivers are already availible. This script
# runs early at bootup, so if the touch driver is mistakenly included as a
# module (as opposed to being compiled directly in) the i2c device may not be
# present yet.
if ! i2c_chardev_present; then
modprobe i2c-dev
log_msg "Please compile I2C_CHARDEV into the kernel"
log_msg "Sleeping 15s to wait for them to show up"
# Pause long enough for for people to notice and fix the kernel config.
# Without this the added delay is small enough that a human might not
# notice that they had just slowed down the boot time by removing the
# driver from the kernel.
sleep 15
fi
local active_fw_ver=""
local new_fw_ver=""
local update_type=""
local update_needed=""
local board_name="$(get_board_name_from_vpd)"
log_msg "Board name detected from VPD as '${board_name}'"
local fw_link="$(find_fw_link_path "${board_name}" "${FW_LINK_BASE}")"
log_msg "Attempting to Load FW: '${fw_link}'"
active_fw_ver="$(get_active_fw_version)"
new_fw_ver="$(get_fw_version_from_disk "${fw_link}")"
log_msg "Active firmware version: ${active_fw_ver}"
log_msg "New firmware version: ${new_fw_ver}"
if [ -z "${active_fw_ver}" ]; then
die "Unable to determine active FW version."
fi
if [ -z "${new_fw_ver}" ]; then
die "Unable to find new FW version on disk."
fi
update_type="$(compare_multipart_version "${active_fw_ver}" "${new_fw_ver}")"
log_update_type "${update_type}"
update_needed="$(is_update_needed "${update_type}")"
if [ "${update_needed}" -eq "${FLAGS_TRUE}" ]; then
log_msg "Update FW to ${new_fw_ver}"
update_firmware "${fw_link}"
# Check if update was successful
active_fw_ver="$(get_active_fw_version)"
update_type="$(compare_multipart_version "${active_fw_ver}" "${new_fw_ver}")"
if [ "${update_type}" -ne "${UPDATE_NOT_NEEDED_UP_TO_DATE}" ]; then
die "Firmware update failed. Current Firmware: ${active_fw_ver}"
fi
log_msg "Update FW succeded. Current Firmware: ${active_fw_ver}"
fi
}
main "$@"