#!/bin/sh

# Copyright (c) 2010 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.

set -e

# Product ID in crash report
CHROMEOS_PRODUCT=ChromeOS

# Should remove the run file when this process finishes.  We don't want
# to always remove it since it may be for pre-existing crash_sender
# process.
CLEAN_UP_RUN_FILE=0

# File whose existence implies crash reports may be sent, and whose
# contents includes our machine's anonymized guid.
CONSENT_ID="/home/chronos/Consent To Send Stats"

# Path to find which is required for computing the crash rate.
FIND="/usr/bin/find"

# Set this to 1 in the environment to allow uploading crash reports
# for unofficial versions.
FORCE_OFFICIAL=${FORCE_OFFICIAL:-0}

# Path to hardware class description.
HWCLASS_PATH="/sys/devices/platform/chromeos_acpi/HWID"

# Ignore PAUSE_CRASH_SENDING file if set.
OVERRIDE_PAUSE_SENDING=${OVERRIDE_PAUSE_SENDING:-0}

# Maximum crashes to send per day.
MAX_CRASH_RATE=${MAX_CRASH_RATE:-32}

# Path to metrics_client.
METRICS_CLIENT="/usr/bin/metrics_client"

# File whose existence mocks crash sending.  If empty we pretend the
# crash sending was successful, otherwise unsuccessful.
MOCK_CRASH_SENDING="/tmp/mock-crash-sending"

# File whose existence causes crash sending to be delayed (for testing).
# Must be stateful to enable testing kernel crashes.
PAUSE_CRASH_SENDING="/var/lib/crash_sender_paused"

# URL to send official build crash reports to.
REPORT_UPLOAD_PROD_URL="https://clients2.google.com/cr/report"

# File whose existence implies we're running and not to start again.
RUN_FILE="/var/run/crash_sender.pid"

# Maximum time to sleep between sends.
SECONDS_SEND_SPREAD=${SECONDS_SEND_SPREAD:-600}

# The syslog tag for all logging we emit.
TAG="$(basename $0)[$$]"

# Directory to store timestamp files indicating the uploads in the past 24
# hours.
TIMESTAMPS_DIR="/var/lib/crash_sender"

# Path to a directory of restricted certificates which includes
# a certificate for ${REPORT_UPLOAD_PROD_URL}.
RESTRICTED_CERTIFICATES_PATH="/usr/share/chromeos-ca-certificates"

# Temp directory for this process.
TMP_DIR=""

lecho() {
  logger -t "${TAG}" "$@"
}

# Returns true if mock is enabled.
is_mock() {
  [ -f "${MOCK_CRASH_SENDING}" ] && return 0
  return 1
}

cleanup() {
  if [ -n "${TMP_DIR}" ]; then
    rm -rf "${TMP_DIR}"
  fi
  if [ ${CLEAN_UP_RUN_FILE} -eq 1 ]; then
    rm -f "${RUN_FILE}"
  fi
  if is_mock; then
    # For testing purposes, emit a message to log so that we
    # know when the test has received all the messages from this run.
    lecho "crash_sender done."
  fi
}

check_not_already_running() {
  set -o noclobber
  if echo $$ 2>/dev/null > "${RUN_FILE}"; then
    # Able to write RUN_FILE without contention.
    CLEAN_UP_RUN_FILE=1
    set +o noclobber
    return
  fi
  set +o noclobber
  local last_pid=$(cat "${RUN_FILE}")
  if [ ! -f "/proc/${last_pid}/cmdline" ]; then
    CLEAN_UP_RUN_FILE=1
    # Note that this write may be executed by two crash_senders who
    # simulataneously reap the existing dangling run file
    echo $$ > "${RUN_FILE}"
    return
  fi
  # This could just be an unrelated process, but it's ok to be conservative.
  lecho "Already running.  Exiting now."
  exit 1
}

is_official() {
  [ ${FORCE_OFFICIAL} -ne 0 ] && return 0
  grep ^CHROMEOS_RELEASE_DESCRIPTION /etc/lsb-release | grep -q Official
}

# Generate a uniform random number in 0..max-1.
generate_uniform_random() {
  local max=$1
  local random="$(od -An -N4 -tu /dev/urandom)"
  echo $((random % max))
}

is_on_3g() {
  # See crosbug.com/3304.
  return 1
}

# Check if sending a crash now does not exceed the maximum 24hr rate and
# commit to doing so, if not.
check_rate() {
  mkdir -p ${TIMESTAMPS_DIR}
  # Only consider minidumps written in the past 24 hours by removing all older.
  ${FIND} "${TIMESTAMPS_DIR}" -mindepth 1 -mmin +$((24 * 60)) \
      -exec rm -- '{}' ';'
  local sends_in_24hrs=$(echo "${TIMESTAMPS_DIR}"/* | wc -w)
  lecho "Current send rate: ${sends_in_24hrs}sends/24hrs"
  if [ ${sends_in_24hrs} -ge ${MAX_CRASH_RATE} ]; then
    lecho "Cannot send more crashes:"
    lecho "  current ${sends_in_24hrs}send/24hrs >= " \
          "max ${MAX_CRASH_RATE}send/24hrs"
    return 1
  fi
  mktemp "${TIMESTAMPS_DIR}"/XXXX > /dev/null
  return 0
}

# Gets the base part of a crash report file, such as
# name.01234.5678.9012 from name.01234.5678.9012.meta
get_base() {
  echo "${1%.*}"
}

get_extension() {
  echo "${1##*.}"
}

# Return which kind of report the given metadata file relates to
get_kind() {
  local payload="$(get_key_value "$1" "payload")"
  if [ ! -r "${payload}" ]; then
    lecho "Missing payload: ${payload}"
    echo "undefined"
    return
  fi
  local kind="$(get_extension "${payload}")"
  if [ "${kind}" = "dmp" ]; then
    echo "minidump"
    return
  fi
  echo "${kind}"
}

get_key_value() {
  if ! grep -q "$2=" "$1"; then
    echo "undefined"
    return
  fi
  grep "$2=" "$1" | cut -d = -f 2-
}

# Return the board name.
get_board() {
  echo $(get_key_value "/etc/lsb-release" "CHROMEOS_RELEASE_BOARD")
}

# Return the hardware class or "undefined".
get_hardware_class() {
  if [ -r "${HWCLASS_PATH}" ]; then
    cat "${HWCLASS_PATH}"
  else
    echo "undefined"
  fi
}

send_crash() {
  local meta_path="$1"
  local report_payload="$(get_key_value "${meta_path}" "payload")"
  local kind="$(get_kind "${meta_path}")"
  local exec_name="$(get_key_value "${meta_path}" "exec_name")"
  local sleep_time=$(generate_uniform_random $SECONDS_SEND_SPREAD)
  local url="${REPORT_UPLOAD_PROD_URL}"
  local chromeos_version="$(get_key_value "${meta_path}" "ver")"
  local board="$(get_board)"
  local hwclass="$(get_hardware_class)"
  local write_payload_size="$(get_key_value "${meta_path}" "payload_size")"
  local log="$(get_key_value "${meta_path}" "log")"
  local sig="$(get_key_value "${meta_path}" "sig")"
  local send_payload_size="$(stat --printf=%s "${report_payload}" 2>/dev/null)"

  local extra_key1="write_payload_size"
  local extra_value1="${write_payload_size}"
  local extra_key2="send_payload_size"
  local extra_value2="${send_payload_size}"
  if [ "${sig}" != "undefined" ]; then
    extra_key1="sig"
    extra_value1="${sig}"
    extra_key2="sig2"
    extra_value2="${sig}"
  elif [ "${log}" != "undefined" ]; then
    # Upload a log file if it was specified.
    extra_key1="log"
    extra_value1="@${log}"
  fi

  lecho "Sending crash:"
  lecho "  Scheduled to send in ${sleep_time}s"
  lecho "  Metadata: ${meta_path} (${kind})"
  lecho "  Payload: ${report_payload}"
  lecho "  Version: ${chromeos_version}"
  if is_mock; then
    lecho "  Product: ${CHROMEOS_PRODUCT}"
    lecho "  URL: ${url}"
    lecho "  Board: ${board}"
    lecho "  HWClass: ${hwclass}"
    lecho "  ${extra_key1}: ${extra_value1}"
    lecho "  ${extra_key2}: ${extra_value2}"
  fi
  lecho "  Exec name: ${exec_name}"
  if is_mock; then
    local mock_in=$(cat "${MOCK_CRASH_SENDING}")
    if [ "${mock_in}" = "" ]; then
      lecho "Mocking successful send"
      return 0
    else
      lecho "Mocking unsuccessful send"
      return 1
    fi
  fi

  if ! sleep ${sleep_time}; then
    lecho "Sleep failed"
    return 1
  fi

  local report_id="${TMP_DIR}/report_id"
  local curl_stderr="${TMP_DIR}/curl_stderr"

  set +e
  curl "${url}" \
    --capath "${RESTRICTED_CERTIFICATES_PATH}" --ciphers HIGH \
    -F "prod=${CHROMEOS_PRODUCT}" \
    -F "ver=${chromeos_version}" \
    -F "upload_file_${kind}=@${report_payload}" \
    -F "board=${board}" \
    -F "hwclass=${hwclass}" \
    -F "exec_name=${exec_name}" \
    -F "${extra_key1}=${extra_value1}" \
    -F "${extra_key2}=${extra_value2}" \
    -F "guid=<${CONSENT_ID}" -o "${report_id}" 2>"${curl_stderr}"
  curl_result=$?
  set -e

  if [ ${curl_result} -eq 0 ]; then
    lecho "Crash report receipt ID $(cat ${report_id})"
  else
    lecho "Crash sending failed with: $(cat ${curl_stderr})"
  fi

  rm -f "${report_id}"

  return ${curl_result}
}

# *.meta files always end with done=1 so we can tell if they are complete.
is_complete_metadata() {
  grep -q "done=1" "$1"
}

# Remove the given report path.
remove_report() {
  local base="${1%.*}"
  rm -f -- "${base}".*
}

# Send all crashes from the given directory.
send_crashes() {
  local dir="$1"

  # Cycle through minidumps, most recent first.  That way if we're about
  # to exceed the daily rate, we send the most recent minidumps.
  if [ ! -d "${dir}" ]; then
    return
  fi

  # Consider any old files which still have no corresponding meta file
  # as orphaned, and remove them.
  for old_file in $(${FIND} "${dir}" -mindepth 1 \
                    -mmin +$((24 * 60)) -type f); do
    if [ ! -e "$(get_base "${old_file}").meta" ]; then
      lecho "Removing old orphaned file: ${old_file}."
      rm -f -- "${old_file}"
    fi
  done

  # Look through all metadata (*.meta) files, if any exist.
  for meta_path in $(ls -1t "${dir}"/*.meta 2>/dev/null); do
    lecho "Considering metadata ${meta_path}."
    local kind=$(get_kind "${meta_path}")

    if [ "${kind}" != "minidump" ] && \
       [ "${kind}" != "kcrash" ] && \
       [ "${kind}" != "log" ]; then
      lecho "Unknown report kind ${kind}.  Removing report."
      remove_report "${meta_path}"
      continue
    fi

    if ${METRICS_CLIENT} -g; then
      lecho "Guest mode has been entered.  Delaying crash sending until exited."
      return 0
    fi

    if ! ${METRICS_CLIENT} -c; then
      lecho "Uploading is disabled.  Removing crash."
      remove_report "${meta_path}"
      continue
    fi

    if ! is_mock && ! is_official; then
      lecho "Not an official OS version.  Removing crash."
      remove_report "${meta_path}"
      continue
    fi

    if is_on_3g; then
      lecho "Not sending crash reports while on 3G, saving for later."
      return 0
    fi

    if ! is_complete_metadata "${meta_path}"; then
      # This report is incomplete, so if it's old, just remove it.
      local old_meta=$(${FIND} "${dir}" -mindepth 1 -name \
        $(basename "${meta_path}") -mmin +$((24 * 60)) -type f)
      if [ -n "${old_meta}" ]; then
        lecho "Removing old incomplete metadata."
        remove_report "${meta_path}"
      else
        lecho "Ignoring recent incomplete metadata."
      fi
      continue
    fi

    if ! check_rate; then
      lecho "Sending ${meta_path} would exceed rate.  Leaving for later."
      return 0
    fi

    if ! send_crash "${meta_path}"; then
      lecho "Problem sending ${meta_path}, not removing."
      continue
    fi

    # Send was successful, now remove.
    lecho "Successfully sent crash ${meta_path} and removing."
    remove_report "${meta_path}"
  done
}

main() {
  trap cleanup EXIT INT TERM
  if [ -e "${PAUSE_CRASH_SENDING}" ] && \
     [ ${OVERRIDE_PAUSE_SENDING} -eq 0 ]; then
    lecho "Exiting early due to ${PAUSE_CRASH_SENDING}."
    exit 1
  fi

  check_not_already_running

  for dependency in "${FIND}" "${METRICS_CLIENT}" \
                    "${RESTRICTED_CERTIFICATES_PATH}"; do
    if [ ! -x "${dependency}" ]; then
      lecho "Fatal: Crash sending disabled: ${dependency} not found."
      exit 1
    fi
  done

  TMP_DIR="$(mktemp -d /tmp/crash_sender.XXXX)"

  # Send system-wide crashes
  send_crashes "/var/spool/crash"

  # Send user-specific crashes
  send_crashes "/home/chronos/user/crash"
}

main
