diff options
Diffstat (limited to 'decoder/source/c_api/ocsd_c_api.cpp')
-rw-r--r-- | decoder/source/c_api/ocsd_c_api.cpp | 632 |
1 files changed, 632 insertions, 0 deletions
diff --git a/decoder/source/c_api/ocsd_c_api.cpp b/decoder/source/c_api/ocsd_c_api.cpp new file mode 100644 index 0000000..750c847 --- /dev/null +++ b/decoder/source/c_api/ocsd_c_api.cpp @@ -0,0 +1,632 @@ +/* + * \file ocsd_c_api.cpp + * \brief OpenCSD : "C" API libary implementation. + * + * \copyright Copyright (c) 2015, ARM Limited. All Rights Reserved. + */ + +/* + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its contributors + * may be used to endorse or promote products derived from this software without + * specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include <cstring> + +/* pull in the C++ decode library */ +#include "opencsd.h" + +/* C-API and wrapper objects */ +#include "opencsd/c_api/opencsd_c_api.h" +#include "ocsd_c_api_obj.h" + +/** MSVC2010 unwanted export workaround */ +#ifdef WIN32 +#if (_MSC_VER == 1600) +#include <new> +namespace std { const nothrow_t nothrow = nothrow_t(); } +#endif +#endif + +/*******************************************************************************/ +/* C API internal helper function declarations */ +/*******************************************************************************/ + +static ocsd_err_t ocsd_create_pkt_sink_cb(ocsd_trace_protocol_t protocol, FnDefPktDataIn pPktInFn, const void *p_context, ITrcTypedBase **ppCBObj ); +static ocsd_err_t ocsd_create_pkt_mon_cb(ocsd_trace_protocol_t protocol, FnDefPktDataMon pPktInFn, const void *p_context, ITrcTypedBase **ppCBObj ); +static ocsd_err_t ocsd_check_and_add_mem_acc_mapper(const dcd_tree_handle_t handle, DecodeTree **ppDT); + +/*******************************************************************************/ +/* C library data - additional data on top of the C++ library objects */ +/*******************************************************************************/ + +/* keep a list of interface objects for a decode tree for later disposal */ +typedef struct _lib_dt_data_list { + std::vector<ITrcTypedBase *> cb_objs; + DefLogStrCBObj s_def_log_str_cb; +} lib_dt_data_list; + +/* map lists to handles */ +static std::map<dcd_tree_handle_t, lib_dt_data_list *> s_data_map; + +/*******************************************************************************/ +/* C API functions */ +/*******************************************************************************/ + +/** Get Library version. Return a 32 bit version in form MMMMnnpp - MMMM = major version, nn = minor version, pp = patch version */ +OCSD_C_API uint32_t ocsd_get_version(void) +{ + return ocsdVersion::vers_num(); +} + +/** Get library version string */ +OCSD_C_API const char * ocsd_get_version_str(void) +{ + return ocsdVersion::vers_str(); +} + + +/*** Decode tree creation etc. */ + +OCSD_C_API dcd_tree_handle_t ocsd_create_dcd_tree(const ocsd_dcd_tree_src_t src_type, const uint32_t deformatterCfgFlags) +{ + dcd_tree_handle_t handle = C_API_INVALID_TREE_HANDLE; + handle = (dcd_tree_handle_t)DecodeTree::CreateDecodeTree(src_type,deformatterCfgFlags); + if(handle != C_API_INVALID_TREE_HANDLE) + { + lib_dt_data_list *pList = new (std::nothrow) lib_dt_data_list; + if(pList != 0) + { + s_data_map.insert(std::pair<dcd_tree_handle_t, lib_dt_data_list *>(handle,pList)); + } + else + { + ocsd_destroy_dcd_tree(handle); + handle = C_API_INVALID_TREE_HANDLE; + } + } + return handle; +} + +OCSD_C_API void ocsd_destroy_dcd_tree(const dcd_tree_handle_t handle) +{ + if(handle != C_API_INVALID_TREE_HANDLE) + { + GenTraceElemCBObj * pIf = (GenTraceElemCBObj *)(((DecodeTree *)handle)->getGenTraceElemOutI()); + if(pIf != 0) + delete pIf; + + /* need to clear any associated callback data. */ + std::map<dcd_tree_handle_t, lib_dt_data_list *>::iterator it; + it = s_data_map.find(handle); + if(it != s_data_map.end()) + { + std::vector<ITrcTypedBase *>::iterator itcb; + itcb = it->second->cb_objs.begin(); + while(itcb != it->second->cb_objs.end()) + { + delete *itcb; + itcb++; + } + it->second->cb_objs.clear(); + delete it->second; + s_data_map.erase(it); + } + DecodeTree::DestroyDecodeTree((DecodeTree *)handle); + } +} + +/*** Decode tree process data */ + +OCSD_C_API ocsd_datapath_resp_t ocsd_dt_process_data(const dcd_tree_handle_t handle, + const ocsd_datapath_op_t op, + const ocsd_trc_index_t index, + const uint32_t dataBlockSize, + const uint8_t *pDataBlock, + uint32_t *numBytesProcessed) +{ + ocsd_datapath_resp_t resp = OCSD_RESP_FATAL_NOT_INIT; + if(handle != C_API_INVALID_TREE_HANDLE) + resp = ((DecodeTree *)handle)->TraceDataIn(op,index,dataBlockSize,pDataBlock,numBytesProcessed); + return resp; +} + +/*** Decode tree - decoder management */ + +OCSD_C_API ocsd_err_t ocsd_dt_create_decoder(const dcd_tree_handle_t handle, + const char *decoder_name, + const int create_flags, + const void *decoder_cfg, + unsigned char *pCSID + ) +{ + ocsd_err_t err = OCSD_OK; + DecodeTree *dt = (DecodeTree *)handle; + std::string dName = decoder_name; + IDecoderMngr *pDcdMngr; + err = OcsdLibDcdRegister::getDecoderRegister()->getDecoderMngrByName(dName,&pDcdMngr); + if(err != OCSD_OK) + return err; + + CSConfig *pConfig = 0; + err = pDcdMngr->createConfigFromDataStruct(&pConfig,decoder_cfg); + if(err != OCSD_OK) + return err; + + err = dt->createDecoder(dName,create_flags,pConfig); + if(err == OCSD_OK) + *pCSID = pConfig->getTraceID(); + delete pConfig; + return err; +} + +OCSD_C_API ocsd_err_t ocsd_dt_remove_decoder( const dcd_tree_handle_t handle, + const unsigned char CSID) +{ + return ((DecodeTree *)handle)->removeDecoder(CSID); +} + +OCSD_C_API ocsd_err_t ocsd_dt_attach_packet_callback( const dcd_tree_handle_t handle, + const unsigned char CSID, + const ocsd_c_api_cb_types callback_type, + void *p_fn_callback_data, + const void *p_context) +{ + ocsd_err_t err = OCSD_OK; + DecodeTree *pDT = static_cast<DecodeTree *>(handle); + DecodeTreeElement *pElem = pDT->getDecoderElement(CSID); + if(pElem == 0) + return OCSD_ERR_INVALID_ID; // cannot find entry for that CSID + + ITrcTypedBase *pDataInSink = 0; // pointer to a sink callback object + switch(callback_type) + { + case OCSD_C_API_CB_PKT_SINK: + err = ocsd_create_pkt_sink_cb(pElem->getProtocol(),(FnDefPktDataIn)p_fn_callback_data,p_context,&pDataInSink); + if(err == OCSD_OK) + err = pElem->getDecoderMngr()->attachPktSink(pElem->getDecoderHandle(), pDataInSink); + break; + + case OCSD_C_API_CB_PKT_MON: + err = ocsd_create_pkt_mon_cb(pElem->getProtocol(),(FnDefPktDataMon)p_fn_callback_data,p_context,&pDataInSink); + if (err == OCSD_OK) + err = pElem->getDecoderMngr()->attachPktMonitor(pElem->getDecoderHandle(), pDataInSink); + break; + + default: + err = OCSD_ERR_INVALID_PARAM_VAL; + } + + if(err == OCSD_OK) + { + if (err == OCSD_OK) + { + // save object pointer for destruction later. + std::map<dcd_tree_handle_t, lib_dt_data_list *>::iterator it; + it = s_data_map.find(handle); + if (it != s_data_map.end()) + it->second->cb_objs.push_back(pDataInSink); + } + else + delete pDataInSink; + } + return err; +} + +OCSD_C_API ocsd_err_t ocsd_dt_get_decode_stats(const dcd_tree_handle_t handle, + const unsigned char CSID, + ocsd_decode_stats_t **p_stats_block) +{ + DecodeTree *pDT = static_cast<DecodeTree *>(handle); + + return pDT->getDecoderStats(CSID, p_stats_block); +} + +OCSD_C_API ocsd_err_t ocsd_dt_reset_decode_stats(const dcd_tree_handle_t handle, + const unsigned char CSID) +{ + DecodeTree *pDT = static_cast<DecodeTree *>(handle); + + return pDT->resetDecoderStats(CSID); +} + +/*** Decode tree set element output */ +OCSD_C_API ocsd_err_t ocsd_dt_set_gen_elem_outfn(const dcd_tree_handle_t handle, FnTraceElemIn pFn, const void *p_context) +{ + + GenTraceElemCBObj * pCBObj = new (std::nothrow)GenTraceElemCBObj(pFn, p_context); + if(pCBObj) + { + ((DecodeTree *)handle)->setGenTraceElemOutI(pCBObj); + return OCSD_OK; + } + return OCSD_ERR_MEM; +} + + +/*** Default error logging */ + +OCSD_C_API ocsd_err_t ocsd_def_errlog_init(const ocsd_err_severity_t verbosity, const int create_output_logger) +{ + if(DecodeTree::getDefaultErrorLogger()->initErrorLogger(verbosity,(bool)(create_output_logger != 0))) + return OCSD_OK; + return OCSD_ERR_NOT_INIT; +} + +OCSD_C_API ocsd_err_t ocsd_def_errlog_config_output(const int output_flags, const char *log_file_name) +{ + ocsdMsgLogger *pLogger = DecodeTree::getDefaultErrorLogger()->getOutputLogger(); + if(pLogger) + { + pLogger->setLogOpts(output_flags & C_API_MSGLOGOUT_MASK); + if(log_file_name != NULL) + { + pLogger->setLogFileName(log_file_name); + } + return OCSD_OK; + } + return OCSD_ERR_NOT_INIT; +} + + +OCSD_C_API ocsd_err_t ocsd_def_errlog_set_strprint_cb(const dcd_tree_handle_t handle, void *p_context, FnDefLoggerPrintStrCB p_str_print_cb) +{ + ocsdMsgLogger *pLogger = DecodeTree::getDefaultErrorLogger()->getOutputLogger(); + if (pLogger) + { + std::map<dcd_tree_handle_t, lib_dt_data_list *>::iterator it; + it = s_data_map.find(handle); + if (it != s_data_map.end()) + { + DefLogStrCBObj *pCBObj = &(it->second->s_def_log_str_cb); + pCBObj->setCBFn(p_context, p_str_print_cb); + pLogger->setStrOutFn(pCBObj); + int logOpts = pLogger->getLogOpts(); + logOpts |= (int)(ocsdMsgLogger::OUT_STR_CB); + pLogger->setLogOpts(logOpts); + return OCSD_OK; + } + } + return OCSD_ERR_NOT_INIT; +} + +OCSD_C_API void ocsd_def_errlog_msgout(const char *msg) +{ + ocsdMsgLogger *pLogger = DecodeTree::getDefaultErrorLogger()->getOutputLogger(); + if(pLogger) + pLogger->LogMsg(msg); +} + +/*** Convert packet to string */ + +OCSD_C_API ocsd_err_t ocsd_pkt_str(const ocsd_trace_protocol_t pkt_protocol, const void *p_pkt, char *buffer, const int buffer_size) +{ + ocsd_err_t err = OCSD_OK; + if((buffer == NULL) || (buffer_size < 2)) + return OCSD_ERR_INVALID_PARAM_VAL; + + std::string pktStr = ""; + buffer[0] = 0; + + switch(pkt_protocol) + { + case OCSD_PROTOCOL_ETMV4I: + trcPrintElemToString<EtmV4ITrcPacket,ocsd_etmv4_i_pkt>(p_pkt, pktStr); + break; + + case OCSD_PROTOCOL_ETMV3: + trcPrintElemToString<EtmV3TrcPacket,ocsd_etmv3_pkt>(p_pkt, pktStr); + break; + + case OCSD_PROTOCOL_STM: + trcPrintElemToString<StmTrcPacket,ocsd_stm_pkt>(p_pkt, pktStr); + break; + + case OCSD_PROTOCOL_PTM: + trcPrintElemToString<PtmTrcPacket,ocsd_ptm_pkt>(p_pkt, pktStr); + break; + + default: + if (OCSD_PROTOCOL_IS_CUSTOM(pkt_protocol)) + err = ocsd_cust_protocol_to_str(pkt_protocol, p_pkt, buffer, buffer_size); + else + err = OCSD_ERR_NO_PROTOCOL; + break; + } + + if(pktStr.size() > 0) + { + strncpy(buffer,pktStr.c_str(),buffer_size-1); + buffer[buffer_size-1] = 0; + } + return err; +} + +OCSD_C_API ocsd_err_t ocsd_gen_elem_str(const ocsd_generic_trace_elem *p_pkt, char *buffer, const int buffer_size) +{ + ocsd_err_t err = OCSD_OK; + if((buffer == NULL) || (buffer_size < 2)) + return OCSD_ERR_INVALID_PARAM_VAL; + std::string str; + trcPrintElemToString<OcsdTraceElement,ocsd_generic_trace_elem>(p_pkt,str); + if(str.size() > 0) + { + strncpy(buffer,str.c_str(),buffer_size -1); + buffer[buffer_size-1] = 0; + } + return err; +} + +/*** Decode tree -- memory accessor control */ + +OCSD_C_API ocsd_err_t ocsd_dt_add_binfile_mem_acc(const dcd_tree_handle_t handle, const ocsd_vaddr_t address, const ocsd_mem_space_acc_t mem_space, const char *filepath) +{ + ocsd_err_t err = OCSD_OK; + DecodeTree *pDT; + err = ocsd_check_and_add_mem_acc_mapper(handle,&pDT); + if(err == OCSD_OK) + err = pDT->addBinFileMemAcc(address,mem_space,filepath); + return err; +} + +OCSD_C_API ocsd_err_t ocsd_dt_add_binfile_region_mem_acc(const dcd_tree_handle_t handle, const ocsd_file_mem_region_t *region_array, const int num_regions, const ocsd_mem_space_acc_t mem_space, const char *filepath) +{ + ocsd_err_t err = OCSD_OK; + DecodeTree *pDT; + err = ocsd_check_and_add_mem_acc_mapper(handle,&pDT); + if(err == OCSD_OK) + err = pDT->addBinFileRegionMemAcc(region_array,num_regions,mem_space,filepath); + return err; +} + +OCSD_C_API ocsd_err_t ocsd_dt_add_buffer_mem_acc(const dcd_tree_handle_t handle, const ocsd_vaddr_t address, const ocsd_mem_space_acc_t mem_space, const uint8_t *p_mem_buffer, const uint32_t mem_length) +{ + ocsd_err_t err = OCSD_OK; + DecodeTree *pDT; + err = ocsd_check_and_add_mem_acc_mapper(handle,&pDT); + if(err == OCSD_OK) + err = pDT->addBufferMemAcc(address,mem_space,p_mem_buffer,mem_length); + return err; +} + +OCSD_C_API ocsd_err_t ocsd_dt_add_callback_mem_acc(const dcd_tree_handle_t handle, const ocsd_vaddr_t st_address, const ocsd_vaddr_t en_address, const ocsd_mem_space_acc_t mem_space, Fn_MemAcc_CB p_cb_func, const void *p_context) +{ + ocsd_err_t err = OCSD_OK; + DecodeTree *pDT; + err = ocsd_check_and_add_mem_acc_mapper(handle,&pDT); + if(err == OCSD_OK) + err = pDT->addCallbackMemAcc(st_address,en_address,mem_space,p_cb_func,p_context); + return err; +} + +OCSD_C_API ocsd_err_t ocsd_dt_add_callback_trcid_mem_acc(const dcd_tree_handle_t handle, const ocsd_vaddr_t st_address, const ocsd_vaddr_t en_address, const ocsd_mem_space_acc_t mem_space, Fn_MemAccID_CB p_cb_func, const void *p_context) +{ + ocsd_err_t err = OCSD_OK; + DecodeTree *pDT; + err = ocsd_check_and_add_mem_acc_mapper(handle, &pDT); + if (err == OCSD_OK) + err = pDT->addCallbackIDMemAcc(st_address, en_address, mem_space, p_cb_func, p_context); + return err; +} + + +OCSD_C_API ocsd_err_t ocsd_dt_remove_mem_acc(const dcd_tree_handle_t handle, const ocsd_vaddr_t st_address, const ocsd_mem_space_acc_t mem_space) +{ + ocsd_err_t err = OCSD_OK; + + if(handle != C_API_INVALID_TREE_HANDLE) + { + DecodeTree *pDT = static_cast<DecodeTree *>(handle); + err = pDT->removeMemAccByAddress(st_address,mem_space); + } + else + err = OCSD_ERR_INVALID_PARAM_VAL; + return err; +} + +OCSD_C_API void ocsd_tl_log_mapped_mem_ranges(const dcd_tree_handle_t handle) +{ + if(handle != C_API_INVALID_TREE_HANDLE) + { + DecodeTree *pDT = static_cast<DecodeTree *>(handle); + pDT->logMappedRanges(); + } +} + +OCSD_C_API void ocsd_gen_elem_init(ocsd_generic_trace_elem *p_pkt, const ocsd_gen_trc_elem_t elem_type) +{ + p_pkt->elem_type = elem_type; + p_pkt->flag_bits = 0; + p_pkt->ptr_extended_data = 0; +} + +OCSD_C_API ocsd_err_t ocsd_dt_set_raw_frame_printer(const dcd_tree_handle_t handle, int flags) +{ + if (handle != C_API_INVALID_TREE_HANDLE) + return ((DecodeTree *)handle)->addRawFramePrinter(0, (uint32_t)flags); + return OCSD_ERR_NOT_INIT; +} + +OCSD_C_API ocsd_err_t ocsd_dt_set_gen_elem_printer(const dcd_tree_handle_t handle) +{ + if (handle != C_API_INVALID_TREE_HANDLE) + return ((DecodeTree *)handle)->addGenElemPrinter(0); + return OCSD_ERR_NOT_INIT; +} + +OCSD_C_API ocsd_err_t ocsd_dt_set_pkt_protocol_printer(const dcd_tree_handle_t handle, uint8_t cs_id, int monitor) +{ + ocsd_err_t err = OCSD_ERR_NOT_INIT; + if (handle != C_API_INVALID_TREE_HANDLE) + { + DecodeTree *p_tree = (DecodeTree *)handle; + err = p_tree->addPacketPrinter(cs_id, (bool)(monitor != 0), 0); + } + return err; +} + +OCSD_C_API void ocsd_err_str(const ocsd_err_t err, char *buffer, const int buffer_size) +{ + std::string err_str; + err_str = ocsdError::getErrorString(ocsdError(OCSD_ERR_SEV_ERROR, err)); + strncpy(buffer, err_str.c_str(), buffer_size - 1); + buffer[buffer_size - 1] = 0; +} + +OCSD_C_API ocsd_err_t ocsd_get_last_err(ocsd_trc_index_t *index, uint8_t *chan_id, char *message, const int message_len) +{ + ocsdError *p_err; + ocsd_err_t err = OCSD_OK; + std::string err_str; + + p_err = DecodeTree::getDefaultErrorLogger()->GetLastError(); + if (p_err) + { + *index = p_err->getErrorIndex(); + *chan_id = p_err->getErrorChanID(); + err_str = p_err->getErrorString(ocsdError(p_err)); + strncpy(message, err_str.c_str(), message_len - 1); + message[message_len - 1] = 0; + err = p_err->getErrorCode(); + } + else + { + message[0] = 0; + *index = OCSD_BAD_TRC_INDEX; + *chan_id = OCSD_BAD_CS_SRC_ID; + } + return err; +} + +/*******************************************************************************/ +/* C API local fns */ +/*******************************************************************************/ +static ocsd_err_t ocsd_create_pkt_sink_cb(ocsd_trace_protocol_t protocol, FnDefPktDataIn pPktInFn, const void *p_context, ITrcTypedBase **ppCBObj ) +{ + ocsd_err_t err = OCSD_OK; + *ppCBObj = 0; + + switch(protocol) + { + case OCSD_PROTOCOL_ETMV4I: + *ppCBObj = new (std::nothrow) PktCBObj<EtmV4ITrcPacket>(pPktInFn,p_context); + break; + + case OCSD_PROTOCOL_ETMV3: + *ppCBObj = new (std::nothrow) PktCBObj<EtmV3TrcPacket>(pPktInFn,p_context); + break; + + case OCSD_PROTOCOL_PTM: + *ppCBObj = new (std::nothrow) PktCBObj<PtmTrcPacket>(pPktInFn,p_context); + break; + + case OCSD_PROTOCOL_STM: + *ppCBObj = new (std::nothrow) PktCBObj<StmTrcPacket>(pPktInFn,p_context); + break; + + default: + if ((protocol >= OCSD_PROTOCOL_CUSTOM_0) && (protocol < OCSD_PROTOCOL_END)) + { + *ppCBObj = new (std::nothrow) PktCBObj<void>(pPktInFn, p_context); + } + else + err = OCSD_ERR_NO_PROTOCOL; + break; + } + + if((*ppCBObj == 0) && (err == OCSD_OK)) + err = OCSD_ERR_MEM; + + return err; +} + +static ocsd_err_t ocsd_create_pkt_mon_cb(ocsd_trace_protocol_t protocol, FnDefPktDataMon pPktInFn, const void *p_context, ITrcTypedBase **ppCBObj ) +{ + ocsd_err_t err = OCSD_OK; + *ppCBObj = 0; + + switch(protocol) + { + case OCSD_PROTOCOL_ETMV4I: + *ppCBObj = new (std::nothrow) PktMonCBObj<EtmV4ITrcPacket>(pPktInFn,p_context); + break; + + case OCSD_PROTOCOL_ETMV3: + *ppCBObj = new (std::nothrow) PktMonCBObj<EtmV3TrcPacket>(pPktInFn,p_context); + break; + + case OCSD_PROTOCOL_PTM: + *ppCBObj = new (std::nothrow) PktMonCBObj<PtmTrcPacket>(pPktInFn,p_context); + break; + + case OCSD_PROTOCOL_STM: + *ppCBObj = new (std::nothrow) PktMonCBObj<StmTrcPacket>(pPktInFn,p_context); + break; + + default: + if ((protocol >= OCSD_PROTOCOL_CUSTOM_0) && (protocol < OCSD_PROTOCOL_END)) + { + *ppCBObj = new (std::nothrow) PktMonCBObj<void>(pPktInFn, p_context); + } + else + err = OCSD_ERR_NO_PROTOCOL; + break; + } + + if((*ppCBObj == 0) && (err == OCSD_OK)) + err = OCSD_ERR_MEM; + + return err; +} + +static ocsd_err_t ocsd_check_and_add_mem_acc_mapper(const dcd_tree_handle_t handle, DecodeTree **ppDT) +{ + *ppDT = 0; + if(handle == C_API_INVALID_TREE_HANDLE) + return OCSD_ERR_INVALID_PARAM_VAL; + *ppDT = static_cast<DecodeTree *>(handle); + if(!(*ppDT)->hasMemAccMapper()) + return (*ppDT)->createMemAccMapper(); + return OCSD_OK; +} + +/*******************************************************************************/ +/* C API Helper objects */ +/*******************************************************************************/ + +/****************** Generic trace element output callback function ************/ +GenTraceElemCBObj::GenTraceElemCBObj(FnTraceElemIn pCBFn, const void *p_context) : + m_c_api_cb_fn(pCBFn), + m_p_cb_context(p_context) +{ +} + +ocsd_datapath_resp_t GenTraceElemCBObj::TraceElemIn(const ocsd_trc_index_t index_sop, + const uint8_t trc_chan_id, + const OcsdTraceElement &elem) +{ + return m_c_api_cb_fn(m_p_cb_context, index_sop, trc_chan_id, &elem); +} + +/* End of File ocsd_c_api.cpp */ |