InProcClientWrapper::InProcClientWrapper(
        std::weak_ptr<std::recursive_mutex> csdkLock, PlatformConfig cfg)
            : m_threadRun(false), m_csdkLock(csdkLock),
              m_cfg { cfg }
    {
        // if the config type is server, we ought to never get called.  If the config type
        // is both, we count on the server to run the thread and do the initialize

        if(m_cfg.mode == ModeType::Client)
        {
            OCTransportFlags serverFlags =
                            static_cast<OCTransportFlags>(m_cfg.serverConnectivity & CT_MASK_FLAGS);
            OCTransportFlags clientFlags =
                            static_cast<OCTransportFlags>(m_cfg.clientConnectivity & CT_MASK_FLAGS);
            OCStackResult result = OCInit1(OC_CLIENT, serverFlags, clientFlags);

            if(OC_STACK_OK != result)
            {
                throw InitializeException(OC::InitException::STACK_INIT_ERROR, result);
            }

            m_threadRun = true;
            m_listeningThread = std::thread(&InProcClientWrapper::listeningFunc, this);
        }
    }
    OCStackResult InProcServerWrapper::start()
    {
        OIC_LOG_V(INFO, TAG, "start ocplatform for server : %d", m_cfg.transportType);

        OCMode initType;
        if(m_cfg.mode == ModeType::Server)
        {
            initType = OC_SERVER;
        }
        else if (m_cfg.mode == ModeType::Both)
        {
            initType = OC_CLIENT_SERVER;
        }
        else if (m_cfg.mode == ModeType::Gateway)
        {
            initType = OC_GATEWAY;
        }
        else
        {
            throw InitializeException(OC::InitException::NOT_CONFIGURED_AS_SERVER,
                                         OC_STACK_INVALID_PARAM);
        }

        OCTransportFlags serverFlags =
                            static_cast<OCTransportFlags>(m_cfg.serverConnectivity & CT_MASK_FLAGS);
        OCTransportFlags clientFlags =
                            static_cast<OCTransportFlags>(m_cfg.clientConnectivity & CT_MASK_FLAGS);
        OCStackResult result = OCInit2(initType, serverFlags, clientFlags,
                                       m_cfg.transportType);

        if(OC_STACK_OK != result)
        {
            throw InitializeException(OC::InitException::STACK_INIT_ERROR, result);
        }

        if (false == m_threadRun)
        {
            m_threadRun = true;
            m_processThread = std::thread(&InProcServerWrapper::processFunc, this);
        }
        return OC_STACK_OK;
    }
    InProcServerWrapper::InProcServerWrapper(
        std::weak_ptr<std::recursive_mutex> csdkLock, PlatformConfig cfg)
     : m_csdkLock(csdkLock)
    {
        OCMode initType;

        if(cfg.mode == ModeType::Server)
        {
            initType = OC_SERVER;
        }
        else if (cfg.mode == ModeType::Both)
        {
            initType = OC_CLIENT_SERVER;
        }
        else if (cfg.mode == ModeType::Gateway)
        {
            initType = OC_GATEWAY;
        }
        else
        {
            throw InitializeException(OC::InitException::NOT_CONFIGURED_AS_SERVER,
                                         OC_STACK_INVALID_PARAM);
        }

        OCTransportFlags serverFlags =
                            static_cast<OCTransportFlags>(cfg.serverConnectivity & CT_MASK_FLAGS);
        OCTransportFlags clientFlags =
                            static_cast<OCTransportFlags>(cfg.clientConnectivity & CT_MASK_FLAGS);
        OCStackResult result = OCInit1(initType, serverFlags, clientFlags);

        if(OC_STACK_OK != result)
        {
            throw InitializeException(OC::InitException::STACK_INIT_ERROR, result);
        }

        m_threadRun = true;
        m_processThread = std::thread(&InProcServerWrapper::processFunc, this);
    }
    OCStackResult InProcServerWrapper::stop()
    {
        OIC_LOG(INFO, TAG, "stop");

        if(m_processThread.joinable())
        {
            m_threadRun = false;
            m_processThread.join();
        }

        OCStackResult res = OCStop();

        if (OC_STACK_OK != res)
        {
           throw InitializeException(OC::InitException::STACK_TERMINATE_ERROR, res);
        }

        return OC_STACK_OK;
    }
InProcClientWrapper::InProcClientWrapper(
    std::weak_ptr<std::recursive_mutex> csdkLock, PlatformConfig cfg)
    : m_threadRun(false), m_csdkLock(csdkLock),
      m_cfg { cfg }
{
    // if the config type is server, we ought to never get called.  If the config type
    // is both, we count on the server to run the thread and do the initialize

    if(m_cfg.mode == ModeType::Client)
    {
        OCStackResult result = OCInit(m_cfg.ipAddress.c_str(), m_cfg.port, OC_CLIENT);

        if(OC_STACK_OK != result)
        {
            throw InitializeException(OC::InitException::STACK_INIT_ERROR, result);
        }

        m_threadRun = true;
        m_listeningThread = std::thread(&InProcClientWrapper::listeningFunc, this);
    }
}