/* Copyright 2020 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.
 *
 * SPDX-License-Identifier: BSD-3-Clause
 */

#ifndef FACTORY_BOOT_KVS__H
#define FACTORY_BOOT_KVS__H

#include <stddef.h>

#define FACTORY_BOOT_KVS_SIZE CONFIG_FACTORY_BOOT_KVS_SIZE

#define FB_KVS_ERROR(fmt, ...) printf("factory_boot KVS: ERROR: " fmt "\n", ##__VA_ARGS__)
#define FB_KVS_INFO(fmt, ...) printkf("factory_boot KVS: INFO: " fmt "\n",  ##__VA_ARGS__)

typedef enum {
	kFbKvsResultOk,
	kFbKvsResultErrorNotInitialized,
	kFbKvsResultNotFound,
	kFbKvsResultTypeMismatch,
	kFbKvsResultBufTooSmall,
	kFbKvsResultInvalid,
	kFbKvsResultInvalidArg,
	kFbKvsResultInvalidData
} FbKvsResult;

typedef enum {
	kFbKvsTypeInvalid,
	kFbKvsTypeString,
	kFbKvsTypeLong,
	kFbKvsTypeULong,
	kFbKvsTypeData
} FbKvsValueType;

/* High-level operations/functions/methods for factory_boot KVS that are
 * platform dependent.
 */
typedef struct {
	/* Reads a buffer of KVS from persistent storage.
	 * Returns kFbKvsResultOk on success, error code otherwise.
	 */
	FbKvsResult (*read)(uint8_t* buf, size_t size);
} FbKvsOps;

/* Reads KVS data via |read| callback.  Allocates and initializes internal
 * structures based on read data.
 * Returns kFbKvsResultOk on success, error code otherwise.
 */
FbKvsResult FbKvsInit(FbKvsOps* ops);

/* Frees all internal allocations */
void FbKvsDeinit(void);

/* Updates |size| to number of key/value pairs in the storage
 * All pairs are contiguously indexed starting at 0.
 * Returns kFbKvsResultOk on success, error code otherwise.
 */
FbKvsResult FbKvsGetNumberOfPairs(size_t* size);

/* Updates |key| to key's name at specific index
 * Returns kFbKvsResultOk on success, error code otherwise
 */
FbKvsResult FbKvsGetKeyByIndex(uint32_t index, char* key, size_t size);

/* Updates |size| to actual value size addressed by |key|
 * Returns kFbKvsResultOk on success, error code otherwise
 */
FbKvsResult FbKvsGetValueSize(const char* key, size_t* size);

/* Get |type| of value addressed by |key|
 * Returns kFbKvsResultOk on success, error code otherwise
 */
FbKvsResult FbKvsGetValueType(const char* key, FbKvsValueType* type);

/* Gets C-string |value| using the |key|.
 * |key| is a C-string.
 * Updates |size| to actual |value| size, it no errors were occurred.
 * Returns kFbKvsResultOk on success, error code otherwise.
 * kFbKvsResultBufTooSmall will be returned if value's buffer is too small.
 */
FbKvsResult FbKvsGetString(const char* key, char* value, size_t* size);
/* Gets 64bit signed int |value| using the |key|.
 * |key| is a C-string.
 * Returns kFbKvsResultOk on success, error code otherwise.
 */
FbKvsResult FbKvsGetLong(const char* key, int64_t* value);
/* Gets 64bit unsigned int |value| using the |key|.
 * |key| is a C-string.
 * Returns kFbKvsResultOk on success, error code otherwise.
 */
FbKvsResult FbKvsGetULong(const char* key, uint64_t* value);
/* Gets raw |data| using the |key|.
 * |key| is a C-string.
 * Updates |size| to actual |value| size, it no errors were occurred.
 * Returns kFbKvsResultOk on success, error code otherwise.
 * kFbKvsResultBufTooSmall will be returned if value's buffer is too small.
 */
FbKvsResult FbKvsGetData(const char* key, uint8_t* data, size_t* size);

#endif /* FACTORY_BOOT_KVS__H */
