////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// Copyright (c) 2020-2021 Qualcomm Technologies, Inc.
// All Rights Reserved.
// Confidential and Proprietary - Qualcomm Technologies, Inc.
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// @file  camxpdnetinterface.h
/// @brief PDNet algorithms interfaces
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////


#ifndef CAMXPDNETINTERFACE_H
#define CAMXPDNETINTERFACE_H

#include "chi.h"
#include "chistatsinterfacedefs.h"
#include "chistatsdebug.h"

#ifdef __cplusplus
extern "C"
{
#endif // __cplusplus

/// Data structures that are exposed to OEM must be packed to have the expected layout.
#pragma pack(push, CDK_PACK_SIZE)


/// @brief PDNetBufFormatDimension Represents the dimension info for the input buffers
typedef struct
{
    ChiBufferFormat         imgBufFmt;          ///< Img Buffer format
    StatsDimension          imgBufDim;          ///< Img buffer dimension
    UINT32                  stride;             ///< Img buffer planeStride
    UINT32                  sliceHeight;        ///< Img buffer plane slice height
    UINT32                  scaleDownRatio;     ///< Img buffer scale down ratio for cv lib
} PDNetBufFormatDimension;

/// @brief PDNetResults  Algorithm output structure
typedef struct
{
    UINT8                   isValid;                                  ///< Flag to check the data validity
    UINT8                   outWidth;                                 ///< PDNet model output width
    UINT8                   outHeight;                                ///< PDNet model output height
    VOID*                   outputMaps;                               ///< Depth & Confidence maps
    SIZE_T                  outputMapsSize;                           ///< Size of output maps buffer
    VOID*                   pLUTBuffer;                               ///< LUT Buffer
} PDNetResults;

/// @brief Identifies the type of input to PDNet algorithm
typedef enum
{
    PDNetInputTypeInvalid         = -1,           ///< Invalid type. Payload: NULL & set size to zero.
    PDNetInputTypeCameraID,                       ///< CameraID,                     UINT32
    PDNetInputTypeRequestNumber,                  ///< Request number                UINT64
    PDNetInputTypeRDIPDAF,                        ///< Input RDI PDAF buffer,        PDNetBufFormatDimension
    PDNetInputTypePreprocessedPD,                 ///< Input Preprocessed PD buffer, PDNetBufFormatDimension
    PDNetInputTypeCount,                          ///< Count of input types
} PDNetAlgoInputType;

/// @brief Represents PDNet inputs base structure to the PDNet algorithm, used as part of PDNetAlgoInputList
typedef struct
{
    VOID*                   pPDNetInput;          ///< Pointer to the payload. See PDNetAlgoInputType for details.
    UINT32                  sizeOfPDNetInput;     ///< Size of input payload
    PDNetAlgoInputType      inputType;            ///< Type of the payload
} PDNetAlgoInput;

/// @brief Represents PDNet module inputs to the PDNet algorithm
typedef struct
{
    PDNetAlgoInput*         pPDNetInputs;             ///< Pointer to PDNetAlgoInput array
    UINT32                  inputCount;               ///< Number of inputs
} PDNetAlgoInputList;

/// @brief Represents PDNet output types
typedef enum
{
    PDNetOutputTypeInvalid            = -1,           ///< Invalid type
    PDNetOutputTypeResults,                           ///< PDNetResults type
    PDNetOutputTypeCount,                             ///< Count of the enum
} PDNetAlgoOutputType;

/// @brief Represents PDNet output from the algorithm
typedef struct
{
    VOID*                   pPDNetOutput;               ///< Pointer to the payload. See PDNetAlgoOutputType for details
                                                        ///  Algorithm implementer needs to do a deep copy to the given memory
    UINT32                  sizeOfPDNetOutput;          ///< Size of input payload pointed to by pPDNetOutput
    UINT32                  sizeOfWrittenPDNetOutput;   ///< Size of payload written back. If no output set to zero.
    PDNetAlgoOutputType     outputType;                 ///< Type of the payload
} PDNetAlgoOutput;

/// @brief Represents PDNet output list from the algorithm
typedef struct
{
    PDNetAlgoOutput*        pPDNetOutputs;      ///< Pointer to PDNetAlgoOutput elements array.
    UINT32                  outputCount;        ///< Number of elements in pPDNetOutputs
} PDNetAlgoOutputList;

/// @brief Represents PDNet Input types
typedef enum
{
    PDNetGetParamInputTypeInvalid = -1,              ///< Invalid type. Payload: NULL & set size to zero
    PDNetGetParamInputTypeCount,                     ///< Count of the enum
} PDNetAlgoGetParamInputType;

/// @brief Represents the input data to query which contains any associated data necessary to support that query
typedef struct
{
    VOID*                           pGetParamInput;         ///< Pointer to input data given in the query info to generate
                                                            ///  the output. See PDNetAlgoGetParamInputType for details.
    UINT32                          sizeOfGetParamInput;    ///< Size of input payload
    PDNetAlgoGetParamInputType      getParamInputType;      ///< Type of the payload
} PDNetAlgoGetParamInput;

/// @brief Represents PDNet module inputs to the PDNet algorithm
typedef struct
{
    PDNetAlgoGetParamInput*       pGetParamInputs;         ///< Pointer to PDNetAlgoGetParamInput array
    UINT32                        getParamInputCount;      ///< Number of inputs
} PDNetAlgoGetParamInputList;

/// @brief Represents PDNet output types
typedef enum
{
    PDNetGetParamOutputTypeInvalid = -1,              ///< Invalid type. Payload: NULL & set size to zero
    PDNetGetParamOutputTypeCount,                     ///< Count of the enum
} PDNetAlgoGetParamOutputType;

/// @brief Represents PDNet get output information from the algorithm
typedef struct
{
    VOID*                           pGetParamOutput;                ///< Pointer to the payload
    UINT32                          sizeOfGetParamOutput;           ///< Size of input payload pointed to by pGetParamOutput
    UINT32                          sizeOfWrittenGetParamOutput;    ///< Size of payload written back. If no output set to zero
    PDNetAlgoGetParamOutputType     getParamOutputType;             ///< Type of the payload
} PDNetAlgoGetParamOutput;

/// @brief Represents PDNet get output list from the algorithm
typedef struct
{
    PDNetAlgoGetParamOutput*        pGetParamOutputs;       ///< Pointer to PDNetAlgorithmOutput array
    UINT32                          getParamOutputCount;    ///< Number of elements in pPDNetOutputs
} PDNetAlgoGetParamOutputList;

/// @brief Defines the PDNet get parameter information
typedef struct
{
    PDNetAlgoGetParamInputList    inputInfoList;    ///< Data set for processing
    PDNetAlgoGetParamOutputList   outputInfoList;   ///< Output requested in the query
} PDNetAlgoGetParam;

/// @brief Identifies the type of input parameter to PDNet algorithm
typedef enum
{
    PDNetSetParamTypeInvalid          = -1,           ///< Invalid type
    PDNetSetParamTypeTuningData,                      ///< Tuning data type
                                                      ///  Payload type: StatsTuningData
    PDNetSetParamTypeCount,                           ///< Count of the enum
} PDNetAlgoSetParamType;

/// @brief Represents PDNet input parameter
typedef struct
{
    const VOID*              pPDNetSetParam;          ///< Pointer to PDNet input param data
                                                      ///  See PDNetAlgoSetParamType for details
    UINT32                   sizeOfSetParam;          ///< Size of data pointed to by pPDNetInputParam
    PDNetAlgoSetParamType    setParamType;            ///< Type of the input parameter
} PDNetAlgoSetParam;

/// @brief Represents PDNet input parameter passed to PDNetAlgorithm::PDNetSetParam()
typedef struct
{
    PDNetAlgoSetParam*          pPDNetSetParams;      ///< Pointer to PDNet input param data
    UINT32                      setParamsCount;       ///< Number of input param parameters
} PDNetAlgoSetParamList;

/// @brief Identifies the type of create parameter to PDNet algorithm
typedef enum
{
    PDNetCreateParamsTypeInvalid      = -1,       ///< Invalid type
    PDNetCreateParamsTypeLogger,                  ///< Logger function
    PDNetCreateParamsTypeCameraInfo,              ///< CameraInfo of type StatsCameraInfo
    PDNetCreateParamsTypeBufDim,                  ///< Buffer Format & Dimensions
    PDNetCreateParamsTypeTuningParams,            ///< Tuning Parameters
    PDNetCreateParamTypeSettingsPtr,              ///< Settings Data Pointer
    PDNetCreateParamsTypeCount,                   ///< Count of PDNetAlgoCreateParamType
} PDNetAlgoCreateParamType;

/// @brief Represents PDNet create parameter base structure, used as part of PDNetAlgoCreateParamList
typedef struct
{
    VOID*                       pCreateParam;           ///< Payload: See PDNetAlgoCreateParamType for details
    UINT32                      SizeOfCreateParam;      ///< Size of payload pointed by data.
    PDNetAlgoCreateParamType    CreateParamType;        ///< Create parameter type
} PDNetAlgoCreateParam;

/// @brief Represents PDNet create parameters information necessary to create PDNet algorithm. See CreatePDNet.
typedef struct
{
    PDNetAlgoCreateParam*     pCreateParams;          ///< A pointer to CreatePDNet array
    UINT32                    CreateParamsCount;      ///< Number of create parameters
} PDNetAlgoCreateParamList;

/// @brief Identifies the type of destroy parameter
typedef enum
{
    PDNetDestroyParamTypeInvalid               = -1,  ///< Type Invalid
    PDNetDestroyParamTypeCameraID,                    ///< Type camera ID
    PDNetDestroyParamTypeCount,                       ///< Count of destroy params
} PDNetAlgoDestroyParamType;

/// @brief Represents PDNet destroy parameter
typedef struct
{
    PDNetAlgoDestroyParamType   destroyParamType;       ///< Type of parameter passed
    VOID*                       pParam;                 ///< Payload of the particular parameter type
    UINT32                      sizeOfParam;            ///< Size of the payload
} PDNetAlgoDestroyParam;

/// @brief Represents PDNet algorithm destroy parameters
typedef struct
{
    PDNetAlgoDestroyParam*      pParamList;         ///< Pointer to PDNet destroy-parameter
    UINT32                      paramCount;         ///< Number of input destroy-parameters
} PDNetAlgoDestroyParamList;

/// @brief Represents PDNet algo settings controlled from camxsettings
typedef struct
{
    BOOL                        profile;        ///< Profile enabled/disabled
    UINT8                       dumpMask;       ///< Dump Mask
} PDNetAlgoSettings;

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// @brief Interface for PDNet algorithm.
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
typedef struct PDNetAlgorithm
{
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PDNetProcess
    ///
    /// @brief  Runs the PDNet algorithm on the given inputs.
    ///
    /// @param  pPDNetAlgorithm      Pointer to PDNetAlgorithm instance
    /// @param  pInputs              Pointer to stats inputs interface
    /// @param  pOutputs             Pointer to stats data output by the algorithm
    ///
    /// @return CDKResultSuccess upon success.
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CDKResult (*PDNetProcess)(
        PDNetAlgorithm*              pPDNetAlgorithm,
        const PDNetAlgoInputList*    pInputs,
        PDNetAlgoOutputList*         pOutputs);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PDNetGetParam
    ///
    /// @brief  This method retrieves the most up-to-date PDNet algorithm information. The output
    ///         is generally updated after calling PDNetAlgorithm::Process()
    ///
    /// @param  pPDNetAlgorithm   Pointer to PDNetAlgorithm instance
    /// @param  pGetParam         Describes the metadata to query for and contains any associated data necessary to
    ///                           support that query
    ///
    /// @return CDKResultSuccess upon success.
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CDKResult(*PDNetGetParam)(
        PDNetAlgorithm*       pPDNetAlgorithm,
        PDNetAlgoGetParam*    pGetParam);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PDNetSetParam
    ///
    /// @brief  Sets parameters to PDNet.
    ///
    /// @param  pPDNetAlgorithm      Pointer to PDNetAlgorithm instance
    /// @param  pSetParams           PDNet input parameters to set.
    ///
    /// @return CDKResultSuccess upon success.
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    CDKResult(*PDNetSetParam)(
        PDNetAlgorithm*                pPDNetAlgorithm,
        const PDNetAlgoSetParamList*   pSetParams);

    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    /// PDNetDestroy
    ///
    /// @brief  This method destroys the derived instance of the interface
    ///
    /// @param  pPDNetAlgorithm       Pointer to PDNetAlgorithm instance
    /// @param  pDestroyParams        Pointer to destroy Param List
    ///
    /// @return None
    ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
    VOID (*PDNetDestroy)(
        PDNetAlgorithm*                    pPDNetAlgorithm,
        const PDNetAlgoDestroyParamList*   pDestroyParams);
} PDNetAlgorithm;

////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/// CreatePDNet
///
/// @brief  This method creates an instance to the PDNetAlgorithm.
///
/// @param  pCreateParams        Pointer to create params
/// @param  ppPDNetAlgorithm     Pointer to the created PDNetAlgorithm instance
///
/// @return CDKResultSuccess upon success.
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
typedef CDKResult (*CREATEPDNet)(
    const PDNetAlgoCreateParamList*   pCreateParams,
    PDNetAlgorithm**                  ppPDNetAlgorithm);

#pragma pack(pop)

#ifdef __cplusplus
}
#endif // __cplusplus

#endif // CAMXPDNETINTERFACE_H
