/*
 * Copyright 2025-2026 NVIDIA CORPORATION & AFFILIATES.  All rights reserved.
 *
 * NOTICE TO LICENSEE:
 *
 * This source code and/or documentation ("Licensed Deliverables") are
 * subject to NVIDIA intellectual property rights under U.S. and
 * international Copyright laws.
 *
 * These Licensed Deliverables contained herein is PROPRIETARY and
 * CONFIDENTIAL to NVIDIA and is being provided under the terms and
 * conditions of a form of NVIDIA software license agreement by and
 * between NVIDIA and Licensee ("License Agreement") or electronically
 * accepted by Licensee.  Notwithstanding any terms or conditions to
 * the contrary in the License Agreement, reproduction or disclosure
 * of the Licensed Deliverables to any third party without the express
 * written consent of NVIDIA is prohibited.
 *
 * NOTWITHSTANDING ANY TERMS OR CONDITIONS TO THE CONTRARY IN THE
 * LICENSE AGREEMENT, NVIDIA MAKES NO REPRESENTATION ABOUT THE
 * SUITABILITY OF THESE LICENSED DELIVERABLES FOR ANY PURPOSE.  IT IS
 * PROVIDED "AS IS" WITHOUT EXPRESS OR IMPLIED WARRANTY OF ANY KIND.
 * NVIDIA DISCLAIMS ALL WARRANTIES WITH REGARD TO THESE LICENSED
 * DELIVERABLES, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY,
 * NONINFRINGEMENT, AND FITNESS FOR A PARTICULAR PURPOSE.
 * NOTWITHSTANDING ANY TERMS OR CONDITIONS TO THE CONTRARY IN THE
 * LICENSE AGREEMENT, IN NO EVENT SHALL NVIDIA BE LIABLE FOR ANY
 * SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL DAMAGES, OR ANY
 * DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
 * WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
 * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
 * OF THESE LICENSED DELIVERABLES.
 *
 * U.S. Government End Users.  These Licensed Deliverables are a
 * "commercial item" as that term is defined at 48 C.F.R. 2.101 (OCT
 * 1995), consisting of "commercial computer software" and "commercial
 * computer software documentation" as such terms are used in 48
 * C.F.R. 12.212 (SEPT 1995) and is provided to the U.S. Government
 * only as a commercial end item.  Consistent with 48 C.F.R.12.212 and
 * 48 C.F.R. 227.7202-1 through 227.7202-4 (JUNE 1995), all
 * U.S. Government End Users acquire the Licensed Deliverables with
 * only those rights set forth herein.
 *
 * Any use of the Licensed Deliverables in individual and commercial
 * software must include, in the user documentation and internal
 * comments to the code, the above Disclaimer and U.S. Government End
 * Users Notice.
 */

#ifndef ECP_ATOM_API_H
#define ECP_ATOM_API_H

#include <stddef.h>
#include <stdint.h>

#include "../macros.h"
#include "../types/cuest_types.h"
#include "../types/cuest_parameter_types.h"
#include "../types/workspace_api.h"

#ifdef __cplusplus
extern "C" {
#endif

/**
 * @brief Create an effective core potential atom from a set of ECPShell.
 * @ingroup ECP
 *
 * An ECP Atom comprises multiple ECP shells, grouped by atomic center.
 * - All buffer pointers must be valid (not NULL).
 * - Each shell, and each array entry, must be valid.
 * - The output handle is only valid after successful creation.
 *
 * @param[in]  handle                cuEST handle. Must not be NULL.
 * @param[in]  numElectrons          Total number of electrons corresponding to the ECP for this atom; must be greater than zero and even.
 * @param[in]  numShells             Specifies number of shells for this atom with \f$ L < L_{max} \f$ ; must be greater than zero. \f$ L_{max} \f$ is equal to \c numShells.
 * @param[in]  shells                Flat CPU array of shell handles \c cuestECPShell_t (size: \c numShells). Must not be NULL and none of the entries may be NULL. The array must contain exactly one shell per angular momentum in ascending order, i.e. the entry at index \c i must have \f$ L == i \f$.
 * @param[in]  topShell              Shell handle (\c cuestECPShell_t) with \f$ L == L_{max} == \f$ \c numShells for this atom. Must not be NULL.
 * @param[in]  parameters            Handle to \c cuestECPAtomParameters_t. Must not be NULL.
 * @param[out] outECPAtom            Pointer for output atom handle. Must not be NULL.
 *
 * All objects on CPU.
 *
 * @return
 *   - \c CUEST_STATUS_SUCCESS on success;
 *   - \c CUEST_STATUS_INVALID_HANDLE if the cuEST handle is NULL;
 *   - \c CUEST_STATUS_NULL_POINTER if any pointer parameter is NULL;
 *   - \c CUEST_STATUS_INVALID_TYPE if opaque handles are not the correct type;
 *   - \c CUEST_STATUS_INVALID_ARGUMENT if \c numElectrons == 0 or \c numShells == 0;
 *   - \c CUEST_STATUS_EXCEPTION if \c numElectrons is odd, a shell is out of order (\c shells[i] with \f$ L != i \f$), or \c topShell does not have \f$ L == \f$ \c numShells;
 *   - \c CUEST_STATUS_EXCEPTION or \c CUEST_STATUS_UNKNOWN_ERROR on other errors.
 */
CUEST_API
cuestStatus_t cuestECPAtomCreate(
    cuestHandle_t handle,
    uint64_t numElectrons,
    uint64_t numShells,
    const cuestECPShell_t* shells,
    const cuestECPShell_t topShell,
    const cuestECPAtomParameters_t parameters, 
    cuestECPAtom_t* outECPAtom);

/**
 * @brief Destroy/free an ECP Atom object and all associated resources.
 * @ingroup ECP
 *
 * After this function is called, the ECP atom handle must not be used.
 *
 * @param[in] atom    ECP Atom handle to destroy; must not be NULL.
 *
 * @return
 *   - \c CUEST_STATUS_SUCCESS on success;
 *   - \c CUEST_STATUS_NULL_POINTER if atom is NULL;
 *   - \c CUEST_STATUS_INVALID_TYPE if the cuEST ECP Atom handle is not of type \c cuestECPAtom_t;
 *   - \c CUEST_STATUS_EXCEPTION or \c CUEST_STATUS_UNKNOWN_ERROR on error.
 */
CUEST_API
cuestStatus_t cuestECPAtomDestroy(
    cuestECPAtom_t atom);


#ifdef __cplusplus
}
#endif

#endif /* ECP_ATOM_API_H */
