Program Listing for File HostAPI.h

Return to documentation for file (include/flamegpu/runtime/HostAPI.h)

#ifndef INCLUDE_FLAMEGPU_RUNTIME_HOSTAPI_H_
#define INCLUDE_FLAMEGPU_RUNTIME_HOSTAPI_H_

#include <cuda_runtime.h>  // required for cudaStream_t. This doesn't require nvcc however, as no device code.
#include <string>
#include <utility>
#include <functional>
#include <unordered_map>
#include <vector>
#include <memory>

#include "flamegpu/simulation/detail/CUDAErrorChecking.cuh"
#include "flamegpu/runtime/random/HostRandom.cuh"
#include "flamegpu/runtime/environment/HostEnvironment.cuh"
#include "flamegpu/runtime/HostAPI_macros.h"
#include "flamegpu/runtime/agent/HostNewAgentAPI.h"
#include "flamegpu/detail/cuda.cuh"
#include "flamegpu/simulation/CUDASimulation.h"

namespace flamegpu {
namespace detail {
class CUDAFatAgent;
class CUDAScatter;
class CUDAMacroEnvironment;
}  // namespace detail
class HostAgentAPI;

class HostAPI {
    friend class HostAgentAPI;
    friend class detail::CUDAFatAgent;

 public:
    // Typedefs repeated from CUDASimulation
    typedef std::vector<NewAgentStorage> AgentDataBuffer;
    typedef std::unordered_map<std::string, AgentDataBuffer> AgentDataBufferStateMap;
    typedef std::unordered_map<std::string, VarOffsetStruct> AgentOffsetMap;
    typedef std::unordered_map<std::string, AgentDataBufferStateMap> AgentDataMap;
    typedef std::unordered_map<std::string, std::shared_ptr<detail::CUDAEnvironmentDirectedGraphBuffers>> CUDADirectedGraphMap;

     explicit HostAPI(CUDASimulation&_agentModel,
        detail::RandomManager &rng,
        detail::CUDAScatter &scatter,
        const AgentOffsetMap &agentOffsets,
        AgentDataMap &agentData,
        const std::shared_ptr<detail::EnvironmentManager> &env,
        const std::shared_ptr<detail::CUDAMacroEnvironment> &macro_env,
        CUDADirectedGraphMap &directed_graph_map,
        unsigned int streamId,
        cudaStream_t stream);
     ~HostAPI();
    HostAgentAPI agent(const std::string &agent_name, const std::string &stateName = ModelData::DEFAULT_STATE);
    const HostRandom random;
    const HostEnvironment environment;

    unsigned int getStepCounter() const;

#ifdef SWIG
    CUDASimulation::Config getCUDAConfig() const { return agentModel.getCUDAConfig(); }
    Simulation::Config getSimulationConfig() const { return agentModel.getSimulationConfig(); }
#else
    const CUDASimulation::Config &getCUDAConfig() const { return agentModel.getCUDAConfig(); }
    const Simulation::Config &getSimulationConfig() const { return agentModel.getSimulationConfig(); }
#endif

    unsigned int getEnsembleRunIndex() const;

#ifdef FLAMEGPU_ADVANCED_API
    cudaStream_t getCUDAStream() { return stream; }
#endif

 private:
    template<typename T>
    void resizeOutputSpace(unsigned int items = 1);
    CUDASimulation &agentModel;
    void *d_output_space;
    size_t d_output_space_size;
    /*
     * Owned by CUDASimulation, this provides memory offsets for agent variables
     * Used for host agent creationg
     */
    const AgentOffsetMap &agentOffsets;
    /*
     * Owned by CUDASimulation, this provides storage for new agents
     * Used for host agent creation, this should be emptied end of each step
     * when new agents are copied to device.
     */
    AgentDataMap &agentData;
    detail::CUDAScatter &scatter;
    const unsigned int streamId;
    cudaStream_t stream;
};

template<typename T>
void HostAPI::resizeOutputSpace(const unsigned int items) {
    if (sizeof(T) * items > d_output_space_size) {
        if (d_output_space_size) {
            gpuErrchk(flamegpu::detail::cuda::cudaFree(d_output_space));
        }
        gpuErrchk(cudaMalloc(&d_output_space, sizeof(T) * items));
        d_output_space_size = sizeof(T) * items;
    }
}

}  // namespace flamegpu

#endif  // INCLUDE_FLAMEGPU_RUNTIME_HOSTAPI_H_