// Copyright 2016 The Fuchsia Authors
// Copyright (c) 2012 Google, Inc.
//
// Use of this source code is governed by a MIT-style
// license that can be found in the LICENSE file or at
// https://opensource.org/licenses/MIT

#include <debug.h>
#include <lib/boot-options/boot-options.h>
#include <lib/console.h>
#include <lib/crashlog.h>
#include <lib/debuglog.h>
#include <lib/jtrace/jtrace.h>
#include <lib/persistent-debuglog.h>
#include <platform.h>
#include <stdio.h>
#include <zircon/compiler.h>
#include <zircon/errors.h>

#include <dev/hw_watchdog.h>
#include <kernel/thread.h>
#include <platform/crashlog.h>
#include <platform/debug.h>

// Common platform halt path.  This handles some tasks we always want to make
// sure we handle before dropping into the common platform specific halt
// routine.
void platform_halt(platform_halt_action suggested_action, zircon_crash_reason_t reason) {
  // Disable the automatic uptime updating.  We are going to attempt to
  // deliberately halt the system, and we don't want the crashlog to indicate a
  // spontaneous reboot.
  PlatformCrashlog::Get().EnableCrashlogUptimeUpdates(false);

  // We are haling on purpose.  Disable the watchdog (if we have one, and if we
  // can) if we plan to halt instead of instigate a reboot.  If we are going to
  // try to actually reboot, pet the dog one last time to give ourselves the
  // maximum amount of time to arrange our graceful reboot.
  bool halt_on_panic = gBootOptions->halt_on_panic;
  if (ENABLE_PANIC_SHELL || halt_on_panic) {
    hw_watchdog_set_enabled(false);
  } else {
    hw_watchdog_pet();
  }

  // Render and stash our crashlog.  crashlog_to_string will decide what should
  // be in the crashlog payload based on the provided crash reason.
  {
    size_t rendered_crashlog_len = 0;
    auto& crashlog = PlatformCrashlog::Get();
    if (ktl::span<char> target = crashlog.GetRenderTarget(); target.size() > 0) {
      rendered_crashlog_len = crashlog_to_string(target, reason);
    }
    crashlog.Finalize(reason, rendered_crashlog_len);
  }

  // This is a graceful reboot, invalidate the persistent dlog (if we have one)
  // and persistent trace buffer (if we have one) so that we don't attempt to
  // recover it during a reboot.
  if (reason == ZirconCrashReason::NoCrash) {
    persistent_dlog_invalidate();
    jtrace_invalidate();
  }

  // Finally, fall into the platform specific halt handler.
  platform_specific_halt(suggested_action, reason, halt_on_panic);
}

namespace {
__NO_RETURN
int cmd_reboot(int argc, const cmd_args* argv, uint32_t flags) {
  bool is_panic_shell = (flags & CMD_FLAG_PANIC) != 0;

  // If we are already panicking, don't repeat the first half of `platform_halt`. Instead,
  // just finish the reboot.
  if (is_panic_shell) {
    platform_specific_halt(HALT_ACTION_REBOOT, ZirconCrashReason::Panic,
                           /*halt_on_panic=*/false);
    // unreachable
  }

  platform_halt(HALT_ACTION_REBOOT, ZirconCrashReason::NoCrash);
}
}  // namespace

STATIC_COMMAND_START
STATIC_COMMAND_MASKED("reboot", "reboot the system", &cmd_reboot, CMD_AVAIL_ALWAYS)
STATIC_COMMAND_END(power)
