/* Copyright 2019 The Fuchsia Authors. All rights reserved.
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 */

/* This is the main library header file, and the only header file callers need
 * to include directly. Most callers only need to call AbrGetBootSlot().
 */

#ifndef SRC_FIRMWARE_LIB_ABR_INCLUDE_LIB_ABR_ABR_H_
#define SRC_FIRMWARE_LIB_ABR_INCLUDE_LIB_ABR_ABR_H_

#include "ops.h"
#include "sysdeps.h"

#ifdef __cplusplus
extern "C" {
#endif

typedef enum {
  kAbrResultOk,
  kAbrResultErrorIo,
  kAbrResultErrorInvalidData,
  kAbrResultErrorUnsupportedVersion,
} AbrResult;

typedef enum {
  kAbrSlotIndexA,
  kAbrSlotIndexB,
  kAbrSlotIndexR,
} AbrSlotIndex;

/* This structure describes the current state of an A/B slot.
 *
 * Note that slot R does not have associated metadata and is always considered bootable and
 * successful. It is only considered active when no other slots are bootable.
 *
 * When metadata is uninitialized, it will be initialized to a state which allows a full set of
 * tries for each slot with slot A as highest priority.
 *
 * Fields:
 *    is_bootable - Whether the slot is expected to be bootable.
 *    is_active - Whether the slot is the highest priority bootable slot. This is not a predictor of
 *                AbrGetBootSlot(), which will account for additional configuration like one-shot
 *                recovery requests.
 *    is_marked_successful - Whether the slot has been marked as having booted successfully since
 *                           the last update.
 *    num_tries_remaining - The number of tries remaining to attempt a successful boot. If this
 *                          reaches zero and a slot has not been marked successful, the slot is
 *                          considered unbootable. This value is only meaningful if |is_bootable| is
 *                          true and |is_marked_successful| is false.
 */
typedef struct {
  bool is_bootable;
  bool is_active;
  bool is_marked_successful;
  uint8_t num_tries_remaining;
} AbrSlotInfo;

/* This function implements the core A/B/R logic. It selects a slot to boot based on the current
 * state of the A/B/R metadata. The following algorithm is used:
 *    - If one-shot recovery has been requested and |update_metadata| is true, or if no bootable A/B
 *      slots exist, choose slot R.
 *    - If at least one valid slot exists, choose the valid slot with the highest priority (that is,
 *      the active slot).
 *
 * When |update_metadata| is true, this function may update the stored metadata in the following
 * ways:
 *    - The retry counter will be modified if a slot is chosen which has not been marked successful.
 *    - The one-shot recovery field will be reset if it is handled.
 *    - Invalid metadata will be overwritten with default valid metadata.
 *    - If the other slot is marked as successful, the success mark will be removed and its retry
 *      counter will be reset to the maximum. This happens because booting the selected slot could
 *      cause the other slot to become unable to successfully boot.
 *
 * Parameters:
 *    abr_ops - A populated instance of AbrOps. If |update_metadata| is false, then the
 *              |write_abr_metadata| op may be NULL.
 *    update_metadata - Whether metadata should be updated. This may be set to false early in boot
 *                      when metadata storage is read-only. If set to false, requests for one-shot
 *                      recovery are ignored because there is no way to reset the request. In cases
 *                      where A/B/R logic is run by multiple layers during boot, the one-shot
 *                      recovery request will be handled by the first layer that is capable of
 *                      handling it.
 *    is_slot_marked_successful - On success, is populated with a boolean which indicates whether
 *                                the chosen slot has been marked as successful. This is provided
 *                                for convenience and can be set to NULL.
 */
AbrSlotIndex AbrGetBootSlot(const AbrOps* abr_ops, bool update_metadata,
                            bool* is_slot_marked_successful);

/* A convenience function which provides the partition label suffix associated with a given
 * |slot_index|. For example, "_a" for kAbrSlotIndexA. If an invalid |slot_index| is provided, the
 * empty string is returned.
 */
const char* AbrGetSlotSuffix(AbrSlotIndex slot_index);

/* Marks the given |slot_index| as active. Returns kAbrResultOk on success.
 *
 * Calling this on kAbrSlotIndexR is an error and kAbrResultErrorInvalidData will be returned.
 *
 * This function is typically used by the OS update system when completing an update. It is not
 * normally used by a bootloader except in response to an explicit operator command.
 *
 * Even though the active slot is just the highest priority bootable slot, marking a slot as active
 * does more than change the priority. Specifically, this function will:
 *    - Mark the slot as bootable with highest priority, reducing the priority of other slots if
 *      necessary.
 *    - Mark the slot as NOT successful.
 *    - Set the tries remaining to the max value.
 */
AbrResult AbrMarkSlotActive(const AbrOps* abr_ops, AbrSlotIndex slot_index);

/* Returns the slot index on which AbrMarkSlotActive was lastly called. The result is stored in
 * |out_slot|.
 *
 * This function is typically used by the recovery system (i.e. the R slot OS) to retry the slot
 * that was lastly marked as active after fixing problems. Specifically, in the event of boot
 * failures where the device ends up in R slot, after issues are fixed, this function can be used to
 * query the slot that was lastly marked active by AbrMarkSlotActive, then AbrMarkSlotActive can be
 * used again to re-mark it as active so that it can be retried.
 *
 * If A/B/R metadata is not valid, it will be reset and slot A will be the default active slot.
 */
AbrResult AbrGetSlotLastMarkedActive(const AbrOps* abr_ops, AbrSlotIndex* out_slot);

/* Marks the given |slot_index| as unbootable. Returns kAbrResultOk on success.
 *
 * Calling this on kAbrSlotIndexR is an error and kAbrResultErrorInvalidData will be returned.
 *
 * This function is typically used by the OS update system before writing to a slot.
 */
AbrResult AbrMarkSlotUnbootable(const AbrOps* abr_ops, AbrSlotIndex slot_index);

/* Marks the given |slot_index| as successful. Returns kAbrResultOk on success.
 *
 * Calling this on an unbootable slot is an error and kAbrResultErrorInvalidData will be
 * returned.
 *
 * Calling this on kAbrSlotIndexR is an error and kAbrResultErrorInvalidData will be returned.
 *
 * This function is typically used by the OS update system after having confirmed that the slot
 * works as intended. It is not normally used by a bootloader except in response to an explicit
 * operator command.
 *
 * Compatibility between the newly successful slot and the other slot is unknown. Even if the other
 * slot was successful at one point, it may no longer be. This function adds a success mark to the
 * given slot but also removes any success mark on the other slot.
 */
AbrResult AbrMarkSlotSuccessful(const AbrOps* abr_ops, AbrSlotIndex slot_index);

/* Gets the current |info| for |slot_index|. On success populates |info| and returns kAbrResultOk.
 */
AbrResult AbrGetSlotInfo(const AbrOps* abr_ops, AbrSlotIndex slot_index, AbrSlotInfo* info);

/* Updates metadata to enable or disable one-shot recovery.
 *
 * This function is typically used by an OS to force recovery even when another bootable slot
 * exists. When AbrGetBootSlot responds to this setting, it also resets the setting so recovery
 * will only be triggered once. If AbrGetBootSlot is called with |update_metadata| set to false,
 * or is otherwise unable to reset the setting, the setting will be ignored.
 */
AbrResult AbrSetOneShotRecovery(const AbrOps* abr_ops, bool enable);

#ifdef __cplusplus
}
#endif

#endif  // SRC_FIRMWARE_LIB_ABR_INCLUDE_LIB_ABR_ABR_H_
