117f65170SRuslan Bukin /*
217f65170SRuslan Bukin  * \file       ocsd_dcd_tree.cpp
317f65170SRuslan Bukin  * \brief      OpenCSD :
417f65170SRuslan Bukin  *
517f65170SRuslan Bukin  * \copyright  Copyright (c) 2015, ARM Limited. All Rights Reserved.
617f65170SRuslan Bukin  */
717f65170SRuslan Bukin 
817f65170SRuslan Bukin 
917f65170SRuslan Bukin /*
1017f65170SRuslan Bukin  * Redistribution and use in source and binary forms, with or without modification,
1117f65170SRuslan Bukin  * are permitted provided that the following conditions are met:
1217f65170SRuslan Bukin  *
1317f65170SRuslan Bukin  * 1. Redistributions of source code must retain the above copyright notice,
1417f65170SRuslan Bukin  * this list of conditions and the following disclaimer.
1517f65170SRuslan Bukin  *
1617f65170SRuslan Bukin  * 2. Redistributions in binary form must reproduce the above copyright notice,
1717f65170SRuslan Bukin  * this list of conditions and the following disclaimer in the documentation
1817f65170SRuslan Bukin  * and/or other materials provided with the distribution.
1917f65170SRuslan Bukin  *
2017f65170SRuslan Bukin  * 3. Neither the name of the copyright holder nor the names of its contributors
2117f65170SRuslan Bukin  * may be used to endorse or promote products derived from this software without
2217f65170SRuslan Bukin  * specific prior written permission.
2317f65170SRuslan Bukin  *
2417f65170SRuslan Bukin  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND
2517f65170SRuslan Bukin  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
2617f65170SRuslan Bukin  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
2717f65170SRuslan Bukin  * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
2817f65170SRuslan Bukin  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
2917f65170SRuslan Bukin  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
3017f65170SRuslan Bukin  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
3117f65170SRuslan Bukin  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
3217f65170SRuslan Bukin  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
3317f65170SRuslan Bukin  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
3417f65170SRuslan Bukin  */
3517f65170SRuslan Bukin 
3617f65170SRuslan Bukin #include "common/ocsd_dcd_tree.h"
3717f65170SRuslan Bukin #include "common/ocsd_lib_dcd_register.h"
3817f65170SRuslan Bukin #include "mem_acc/trc_mem_acc_mapper.h"
3917f65170SRuslan Bukin 
4017f65170SRuslan Bukin /***************************************************************/
4117f65170SRuslan Bukin ITraceErrorLog *DecodeTree::s_i_error_logger = &DecodeTree::s_error_logger;
4217f65170SRuslan Bukin std::list<DecodeTree *> DecodeTree::s_trace_dcd_trees;  /**< list of pointers to decode tree objects */
4317f65170SRuslan Bukin ocsdDefaultErrorLogger DecodeTree::s_error_logger;     /**< The library default error logger */
4417f65170SRuslan Bukin TrcIDecode DecodeTree::s_instruction_decoder;           /**< default instruction decode library */
4517f65170SRuslan Bukin 
CreateDecodeTree(const ocsd_dcd_tree_src_t src_type,uint32_t formatterCfgFlags)4617f65170SRuslan Bukin DecodeTree *DecodeTree::CreateDecodeTree(const ocsd_dcd_tree_src_t src_type, uint32_t formatterCfgFlags)
4717f65170SRuslan Bukin {
4817f65170SRuslan Bukin     DecodeTree *dcd_tree = new (std::nothrow) DecodeTree();
4917f65170SRuslan Bukin     if(dcd_tree != 0)
5017f65170SRuslan Bukin     {
5117f65170SRuslan Bukin         if(dcd_tree->initialise(src_type, formatterCfgFlags))
5217f65170SRuslan Bukin         {
5317f65170SRuslan Bukin             s_trace_dcd_trees.push_back(dcd_tree);
5417f65170SRuslan Bukin         }
5517f65170SRuslan Bukin         else
5617f65170SRuslan Bukin         {
5717f65170SRuslan Bukin             delete dcd_tree;
5817f65170SRuslan Bukin             dcd_tree = 0;
5917f65170SRuslan Bukin         }
6017f65170SRuslan Bukin     }
6117f65170SRuslan Bukin     return dcd_tree;
6217f65170SRuslan Bukin }
6317f65170SRuslan Bukin 
DestroyDecodeTree(DecodeTree * p_dcd_tree)6417f65170SRuslan Bukin void DecodeTree::DestroyDecodeTree(DecodeTree *p_dcd_tree)
6517f65170SRuslan Bukin {
6617f65170SRuslan Bukin     std::list<DecodeTree *>::iterator it;
6717f65170SRuslan Bukin     bool bDestroyed = false;
6817f65170SRuslan Bukin     it = s_trace_dcd_trees.begin();
6917f65170SRuslan Bukin     while(!bDestroyed && (it != s_trace_dcd_trees.end()))
7017f65170SRuslan Bukin     {
7117f65170SRuslan Bukin         if(*it == p_dcd_tree)
7217f65170SRuslan Bukin         {
7317f65170SRuslan Bukin             s_trace_dcd_trees.erase(it);
7417f65170SRuslan Bukin             delete p_dcd_tree;
7517f65170SRuslan Bukin             bDestroyed = true;
7617f65170SRuslan Bukin         }
7717f65170SRuslan Bukin         else
7817f65170SRuslan Bukin             it++;
7917f65170SRuslan Bukin     }
8017f65170SRuslan Bukin }
8117f65170SRuslan Bukin 
setAlternateErrorLogger(ITraceErrorLog * p_error_logger)8217f65170SRuslan Bukin void DecodeTree::setAlternateErrorLogger(ITraceErrorLog *p_error_logger)
8317f65170SRuslan Bukin {
8417f65170SRuslan Bukin     if(p_error_logger)
8517f65170SRuslan Bukin         s_i_error_logger = p_error_logger;
8617f65170SRuslan Bukin     else
8717f65170SRuslan Bukin         s_i_error_logger = &s_error_logger;
8817f65170SRuslan Bukin }
8917f65170SRuslan Bukin 
9017f65170SRuslan Bukin /***************************************************************/
9117f65170SRuslan Bukin 
DecodeTree()9217f65170SRuslan Bukin DecodeTree::DecodeTree() :
9317f65170SRuslan Bukin     m_i_instr_decode(&s_instruction_decoder),
9417f65170SRuslan Bukin     m_i_mem_access(0),
9517f65170SRuslan Bukin     m_i_gen_elem_out(0),
9617f65170SRuslan Bukin     m_i_decoder_root(0),
9717f65170SRuslan Bukin     m_frame_deformatter_root(0),
9817f65170SRuslan Bukin     m_decode_elem_iter(0),
9917f65170SRuslan Bukin     m_default_mapper(0),
10017f65170SRuslan Bukin     m_created_mapper(false)
10117f65170SRuslan Bukin {
10217f65170SRuslan Bukin     for(int i = 0; i < 0x80; i++)
10317f65170SRuslan Bukin         m_decode_elements[i] = 0;
10417f65170SRuslan Bukin 
10517f65170SRuslan Bukin      // reset the global demux stats.
10617f65170SRuslan Bukin     m_demux_stats.frame_bytes = 0;
10717f65170SRuslan Bukin     m_demux_stats.no_id_bytes = 0;
108*fc502085SRuslan Bukin     m_demux_stats.valid_id_bytes = 0;
10917f65170SRuslan Bukin     m_demux_stats.unknown_id_bytes = 0;
11017f65170SRuslan Bukin     m_demux_stats.reserved_id_bytes = 0;
11117f65170SRuslan Bukin }
11217f65170SRuslan Bukin 
~DecodeTree()11317f65170SRuslan Bukin DecodeTree::~DecodeTree()
11417f65170SRuslan Bukin {
11517f65170SRuslan Bukin     destroyMemAccMapper();
11617f65170SRuslan Bukin     for(uint8_t i = 0; i < 0x80; i++)
11717f65170SRuslan Bukin     {
11817f65170SRuslan Bukin         destroyDecodeElement(i);
11917f65170SRuslan Bukin     }
12017f65170SRuslan Bukin     PktPrinterFact::destroyAllPrinters(m_printer_list);
12117f65170SRuslan Bukin     delete m_frame_deformatter_root;
12217f65170SRuslan Bukin }
12317f65170SRuslan Bukin 
12417f65170SRuslan Bukin 
12517f65170SRuslan Bukin 
TraceDataIn(const ocsd_datapath_op_t op,const ocsd_trc_index_t index,const uint32_t dataBlockSize,const uint8_t * pDataBlock,uint32_t * numBytesProcessed)12617f65170SRuslan Bukin ocsd_datapath_resp_t DecodeTree::TraceDataIn( const ocsd_datapath_op_t op,
12717f65170SRuslan Bukin                                                const ocsd_trc_index_t index,
12817f65170SRuslan Bukin                                                const uint32_t dataBlockSize,
12917f65170SRuslan Bukin                                                const uint8_t *pDataBlock,
13017f65170SRuslan Bukin                                                uint32_t *numBytesProcessed)
13117f65170SRuslan Bukin {
13217f65170SRuslan Bukin     if(m_i_decoder_root)
13317f65170SRuslan Bukin         return m_i_decoder_root->TraceDataIn(op,index,dataBlockSize,pDataBlock,numBytesProcessed);
13417f65170SRuslan Bukin     *numBytesProcessed = 0;
13517f65170SRuslan Bukin     return OCSD_RESP_FATAL_NOT_INIT;
13617f65170SRuslan Bukin }
13717f65170SRuslan Bukin 
13817f65170SRuslan Bukin /* set key interfaces - attach / replace on any existing tree components */
setInstrDecoder(IInstrDecode * i_instr_decode)13917f65170SRuslan Bukin void DecodeTree::setInstrDecoder(IInstrDecode *i_instr_decode)
14017f65170SRuslan Bukin {
14117f65170SRuslan Bukin     uint8_t elemID;
14217f65170SRuslan Bukin     DecodeTreeElement *pElem = 0;
14317f65170SRuslan Bukin 
14417f65170SRuslan Bukin     pElem = getFirstElement(elemID);
14517f65170SRuslan Bukin     while(pElem != 0)
14617f65170SRuslan Bukin     {
14717f65170SRuslan Bukin         pElem->getDecoderMngr()->attachInstrDecoder(pElem->getDecoderHandle(),i_instr_decode);
14817f65170SRuslan Bukin         pElem = getNextElement(elemID);
14917f65170SRuslan Bukin     }
15017f65170SRuslan Bukin }
15117f65170SRuslan Bukin 
setMemAccessI(ITargetMemAccess * i_mem_access)15217f65170SRuslan Bukin void DecodeTree::setMemAccessI(ITargetMemAccess *i_mem_access)
15317f65170SRuslan Bukin {
15417f65170SRuslan Bukin     uint8_t elemID;
15517f65170SRuslan Bukin     DecodeTreeElement *pElem = 0;
15617f65170SRuslan Bukin 
15717f65170SRuslan Bukin     pElem = getFirstElement(elemID);
15817f65170SRuslan Bukin     while(pElem != 0)
15917f65170SRuslan Bukin     {
16017f65170SRuslan Bukin         pElem->getDecoderMngr()->attachMemAccessor(pElem->getDecoderHandle(),i_mem_access);
16117f65170SRuslan Bukin         pElem = getNextElement(elemID);
16217f65170SRuslan Bukin     }
16317f65170SRuslan Bukin     m_i_mem_access = i_mem_access;
16417f65170SRuslan Bukin }
16517f65170SRuslan Bukin 
setGenTraceElemOutI(ITrcGenElemIn * i_gen_trace_elem)16617f65170SRuslan Bukin void DecodeTree::setGenTraceElemOutI(ITrcGenElemIn *i_gen_trace_elem)
16717f65170SRuslan Bukin {
16817f65170SRuslan Bukin     uint8_t elemID;
16917f65170SRuslan Bukin     DecodeTreeElement *pElem = 0;
17017f65170SRuslan Bukin 
17117f65170SRuslan Bukin     pElem = getFirstElement(elemID);
17217f65170SRuslan Bukin     while(pElem != 0)
17317f65170SRuslan Bukin     {
17417f65170SRuslan Bukin         pElem->getDecoderMngr()->attachOutputSink(pElem->getDecoderHandle(),i_gen_trace_elem);
17517f65170SRuslan Bukin         pElem = getNextElement(elemID);
17617f65170SRuslan Bukin     }
17717f65170SRuslan Bukin }
17817f65170SRuslan Bukin 
createMemAccMapper(memacc_mapper_t type)17917f65170SRuslan Bukin ocsd_err_t DecodeTree::createMemAccMapper(memacc_mapper_t type /* = MEMACC_MAP_GLOBAL*/ )
18017f65170SRuslan Bukin {
18117f65170SRuslan Bukin     // clean up any old one
18217f65170SRuslan Bukin     destroyMemAccMapper();
18317f65170SRuslan Bukin 
18417f65170SRuslan Bukin     // make a new one
18517f65170SRuslan Bukin     switch(type)
18617f65170SRuslan Bukin     {
18717f65170SRuslan Bukin     default:
18817f65170SRuslan Bukin     case MEMACC_MAP_GLOBAL:
18917f65170SRuslan Bukin         m_default_mapper = new (std::nothrow) TrcMemAccMapGlobalSpace();
19017f65170SRuslan Bukin         break;
19117f65170SRuslan Bukin     }
19217f65170SRuslan Bukin 
19317f65170SRuslan Bukin     // set the access interface
19417f65170SRuslan Bukin     if(m_default_mapper)
19517f65170SRuslan Bukin     {
19617f65170SRuslan Bukin         m_created_mapper = true;
19717f65170SRuslan Bukin         setMemAccessI(m_default_mapper);
19817f65170SRuslan Bukin         m_default_mapper->setErrorLog(s_i_error_logger);
19917f65170SRuslan Bukin     }
20017f65170SRuslan Bukin 
20117f65170SRuslan Bukin     return (m_default_mapper != 0) ? OCSD_OK : OCSD_ERR_MEM;
20217f65170SRuslan Bukin }
20317f65170SRuslan Bukin 
setExternMemAccMapper(TrcMemAccMapper * pMapper)20417f65170SRuslan Bukin void DecodeTree::setExternMemAccMapper(TrcMemAccMapper* pMapper)
20517f65170SRuslan Bukin {
20617f65170SRuslan Bukin     destroyMemAccMapper();  // destroy any existing mapper - if decode tree created it.
20717f65170SRuslan Bukin     m_default_mapper = pMapper;
20817f65170SRuslan Bukin }
20917f65170SRuslan Bukin 
destroyMemAccMapper()21017f65170SRuslan Bukin void DecodeTree::destroyMemAccMapper()
21117f65170SRuslan Bukin {
21217f65170SRuslan Bukin     if(m_default_mapper && m_created_mapper)
21317f65170SRuslan Bukin     {
21417f65170SRuslan Bukin         m_default_mapper->RemoveAllAccessors();
21517f65170SRuslan Bukin         delete m_default_mapper;
21617f65170SRuslan Bukin         m_default_mapper = 0;
21717f65170SRuslan Bukin         m_created_mapper = false;
21817f65170SRuslan Bukin     }
21917f65170SRuslan Bukin }
22017f65170SRuslan Bukin 
logMappedRanges()22117f65170SRuslan Bukin void DecodeTree::logMappedRanges()
22217f65170SRuslan Bukin {
22317f65170SRuslan Bukin     if(m_default_mapper)
22417f65170SRuslan Bukin         m_default_mapper->logMappedRanges();
22517f65170SRuslan Bukin }
22617f65170SRuslan Bukin 
22717f65170SRuslan Bukin /* Memory accessor creation - all on default mem accessor using the 0 CSID for global core space. */
addBufferMemAcc(const ocsd_vaddr_t address,const ocsd_mem_space_acc_t mem_space,const uint8_t * p_mem_buffer,const uint32_t mem_length)22817f65170SRuslan Bukin ocsd_err_t DecodeTree::addBufferMemAcc(const ocsd_vaddr_t address, const ocsd_mem_space_acc_t mem_space, const uint8_t *p_mem_buffer, const uint32_t mem_length)
22917f65170SRuslan Bukin {
23017f65170SRuslan Bukin     if(!hasMemAccMapper())
23117f65170SRuslan Bukin         return OCSD_ERR_NOT_INIT;
23217f65170SRuslan Bukin 
23317f65170SRuslan Bukin     // need a valid memory buffer, and a least enough bytes for one opcode.
23417f65170SRuslan Bukin     if((p_mem_buffer == 0) || (mem_length < 4))
23517f65170SRuslan Bukin         return OCSD_ERR_INVALID_PARAM_VAL;
23617f65170SRuslan Bukin 
23717f65170SRuslan Bukin     TrcMemAccessorBase *p_accessor;
23817f65170SRuslan Bukin     ocsd_err_t err = TrcMemAccFactory::CreateBufferAccessor(&p_accessor, address, p_mem_buffer, mem_length);
23917f65170SRuslan Bukin     if(err == OCSD_OK)
24017f65170SRuslan Bukin     {
24117f65170SRuslan Bukin         TrcMemAccBufPtr *pMBuffAcc = dynamic_cast<TrcMemAccBufPtr *>(p_accessor);
24217f65170SRuslan Bukin         if(pMBuffAcc)
24317f65170SRuslan Bukin         {
24417f65170SRuslan Bukin             pMBuffAcc->setMemSpace(mem_space);
24517f65170SRuslan Bukin             err = m_default_mapper->AddAccessor(p_accessor,0);
24617f65170SRuslan Bukin         }
24717f65170SRuslan Bukin         else
24817f65170SRuslan Bukin             err = OCSD_ERR_MEM;    // wrong type of object - treat as mem error
24917f65170SRuslan Bukin 
25017f65170SRuslan Bukin         if(err != OCSD_OK)
25117f65170SRuslan Bukin             TrcMemAccFactory::DestroyAccessor(p_accessor);
25217f65170SRuslan Bukin     }
25317f65170SRuslan Bukin     return err;
25417f65170SRuslan Bukin }
25517f65170SRuslan Bukin 
addBinFileMemAcc(const ocsd_vaddr_t address,const ocsd_mem_space_acc_t mem_space,const std::string & filepath)25617f65170SRuslan Bukin ocsd_err_t DecodeTree::addBinFileMemAcc(const ocsd_vaddr_t address, const ocsd_mem_space_acc_t mem_space, const std::string &filepath)
25717f65170SRuslan Bukin {
25817f65170SRuslan Bukin     if(!hasMemAccMapper())
25917f65170SRuslan Bukin         return OCSD_ERR_NOT_INIT;
26017f65170SRuslan Bukin 
26117f65170SRuslan Bukin     if(filepath.length() == 0)
26217f65170SRuslan Bukin         return OCSD_ERR_INVALID_PARAM_VAL;
26317f65170SRuslan Bukin 
26417f65170SRuslan Bukin     TrcMemAccessorBase *p_accessor;
26517f65170SRuslan Bukin     ocsd_err_t err = TrcMemAccFactory::CreateFileAccessor(&p_accessor,filepath,address);
26617f65170SRuslan Bukin 
26717f65170SRuslan Bukin     if(err == OCSD_OK)
26817f65170SRuslan Bukin     {
26917f65170SRuslan Bukin         TrcMemAccessorFile *pAcc = dynamic_cast<TrcMemAccessorFile *>(p_accessor);
27017f65170SRuslan Bukin         if(pAcc)
27117f65170SRuslan Bukin         {
27217f65170SRuslan Bukin             pAcc->setMemSpace(mem_space);
27317f65170SRuslan Bukin             err = m_default_mapper->AddAccessor(pAcc,0);
27417f65170SRuslan Bukin         }
27517f65170SRuslan Bukin         else
27617f65170SRuslan Bukin             err = OCSD_ERR_MEM;    // wrong type of object - treat as mem error
27717f65170SRuslan Bukin 
27817f65170SRuslan Bukin         if(err != OCSD_OK)
27917f65170SRuslan Bukin             TrcMemAccFactory::DestroyAccessor(p_accessor);
28017f65170SRuslan Bukin     }
28117f65170SRuslan Bukin     return err;
28217f65170SRuslan Bukin 
28317f65170SRuslan Bukin }
28417f65170SRuslan Bukin 
addBinFileRegionMemAcc(const ocsd_file_mem_region_t * region_array,const int num_regions,const ocsd_mem_space_acc_t mem_space,const std::string & filepath)28517f65170SRuslan Bukin ocsd_err_t DecodeTree::addBinFileRegionMemAcc(const ocsd_file_mem_region_t *region_array, const int num_regions, const ocsd_mem_space_acc_t mem_space, const std::string &filepath)
28617f65170SRuslan Bukin {
28717f65170SRuslan Bukin     if(!hasMemAccMapper())
28817f65170SRuslan Bukin         return OCSD_ERR_NOT_INIT;
28917f65170SRuslan Bukin 
29017f65170SRuslan Bukin     if((region_array == 0) || (num_regions == 0) || (filepath.length() == 0))
29117f65170SRuslan Bukin         return OCSD_ERR_INVALID_PARAM_VAL;
29217f65170SRuslan Bukin 
29317f65170SRuslan Bukin     TrcMemAccessorBase *p_accessor;
29417f65170SRuslan Bukin     int curr_region_idx = 0;
29517f65170SRuslan Bukin 
29617f65170SRuslan Bukin     // add first region during the creation of the file accessor.
29717f65170SRuslan Bukin     ocsd_err_t err = TrcMemAccFactory::CreateFileAccessor(&p_accessor,filepath,region_array[curr_region_idx].start_address,region_array[curr_region_idx].file_offset, region_array[curr_region_idx].region_size);
29817f65170SRuslan Bukin     if(err == OCSD_OK)
29917f65170SRuslan Bukin     {
30017f65170SRuslan Bukin         TrcMemAccessorFile *pAcc = dynamic_cast<TrcMemAccessorFile *>(p_accessor);
30117f65170SRuslan Bukin         if(pAcc)
30217f65170SRuslan Bukin         {
30317f65170SRuslan Bukin             // add additional regions to the file accessor.
30417f65170SRuslan Bukin             curr_region_idx++;
30517f65170SRuslan Bukin             while(curr_region_idx < num_regions)
30617f65170SRuslan Bukin             {
30717f65170SRuslan Bukin                 pAcc->AddOffsetRange(region_array[curr_region_idx].start_address,
30817f65170SRuslan Bukin                                         region_array[curr_region_idx].region_size,
30917f65170SRuslan Bukin                                         region_array[curr_region_idx].file_offset);
31017f65170SRuslan Bukin                 curr_region_idx++;
31117f65170SRuslan Bukin             }
31217f65170SRuslan Bukin             pAcc->setMemSpace(mem_space);
31317f65170SRuslan Bukin 
31417f65170SRuslan Bukin             // add the accessor to the map.
31517f65170SRuslan Bukin             err = m_default_mapper->AddAccessor(pAcc,0);
31617f65170SRuslan Bukin         }
31717f65170SRuslan Bukin         else
318*fc502085SRuslan Bukin             err = OCSD_ERR_MEM;    // wrong type of object - treat as mem error
319*fc502085SRuslan Bukin 
320*fc502085SRuslan Bukin         if(err != OCSD_OK)
321*fc502085SRuslan Bukin             TrcMemAccFactory::DestroyAccessor(p_accessor);
322*fc502085SRuslan Bukin     }
323*fc502085SRuslan Bukin     return err;
324*fc502085SRuslan Bukin }
325*fc502085SRuslan Bukin 
updateBinFileRegionMemAcc(const ocsd_file_mem_region_t * region_array,const int num_regions,const ocsd_mem_space_acc_t mem_space,const std::string & filepath)326*fc502085SRuslan Bukin ocsd_err_t DecodeTree::updateBinFileRegionMemAcc(const ocsd_file_mem_region_t *region_array, const int num_regions, const ocsd_mem_space_acc_t mem_space, const std::string &filepath)
327*fc502085SRuslan Bukin {
328*fc502085SRuslan Bukin     if (!hasMemAccMapper())
329*fc502085SRuslan Bukin         return OCSD_ERR_NOT_INIT;
330*fc502085SRuslan Bukin 
331*fc502085SRuslan Bukin     if ((region_array == 0) || (num_regions == 0) || (filepath.length() == 0))
332*fc502085SRuslan Bukin         return OCSD_ERR_INVALID_PARAM_VAL;
333*fc502085SRuslan Bukin 
334*fc502085SRuslan Bukin     TrcMemAccessorFile *pAcc = TrcMemAccessorFile::getExistingFileAccessor(filepath);
335*fc502085SRuslan Bukin     if (!pAcc)
336*fc502085SRuslan Bukin         return OCSD_ERR_INVALID_PARAM_VAL;
337*fc502085SRuslan Bukin 
338*fc502085SRuslan Bukin     int curr_region_idx = 0;
339*fc502085SRuslan Bukin     while (curr_region_idx < num_regions)
340*fc502085SRuslan Bukin     {
341*fc502085SRuslan Bukin         // check "new" range
342*fc502085SRuslan Bukin         if (!pAcc->addrStartOfRange(region_array[curr_region_idx].start_address))
343*fc502085SRuslan Bukin         {
344*fc502085SRuslan Bukin             // ensure adds cleanly
345*fc502085SRuslan Bukin             if (!pAcc->AddOffsetRange(region_array[curr_region_idx].start_address,
346*fc502085SRuslan Bukin                 region_array[curr_region_idx].region_size,
347*fc502085SRuslan Bukin                 region_array[curr_region_idx].file_offset))
34817f65170SRuslan Bukin                 return OCSD_ERR_INVALID_PARAM_VAL;  // otherwise bail out
34917f65170SRuslan Bukin         }
35017f65170SRuslan Bukin         curr_region_idx++;
35117f65170SRuslan Bukin     }
35217f65170SRuslan Bukin     return OCSD_OK;
35317f65170SRuslan Bukin }
initCallbackMemAcc(const ocsd_vaddr_t st_address,const ocsd_vaddr_t en_address,const ocsd_mem_space_acc_t mem_space,void * p_cb_func,bool IDfn,const void * p_context)35417f65170SRuslan Bukin ocsd_err_t DecodeTree::initCallbackMemAcc(const ocsd_vaddr_t st_address, const ocsd_vaddr_t en_address,
35517f65170SRuslan Bukin     const ocsd_mem_space_acc_t mem_space, void *p_cb_func, bool IDfn, const void *p_context)
35617f65170SRuslan Bukin {
35717f65170SRuslan Bukin     if(!hasMemAccMapper())
35817f65170SRuslan Bukin         return OCSD_ERR_NOT_INIT;
35917f65170SRuslan Bukin 
36017f65170SRuslan Bukin     if(p_cb_func == 0)
36117f65170SRuslan Bukin         return OCSD_ERR_INVALID_PARAM_VAL;
362*fc502085SRuslan Bukin 
363*fc502085SRuslan Bukin     TrcMemAccessorBase *p_accessor;
364*fc502085SRuslan Bukin     ocsd_err_t err = TrcMemAccFactory::CreateCBAccessor(&p_accessor, st_address, en_address, mem_space);
365*fc502085SRuslan Bukin     if(err == OCSD_OK)
366*fc502085SRuslan Bukin     {
36717f65170SRuslan Bukin         TrcMemAccCB *pCBAcc = dynamic_cast<TrcMemAccCB *>(p_accessor);
36817f65170SRuslan Bukin         if(pCBAcc)
36917f65170SRuslan Bukin         {
37017f65170SRuslan Bukin             if (IDfn)
37117f65170SRuslan Bukin                 pCBAcc->setCBIDIfFn((Fn_MemAccID_CB)p_cb_func, p_context);
37217f65170SRuslan Bukin             else
37317f65170SRuslan Bukin                 pCBAcc->setCBIfFn((Fn_MemAcc_CB)p_cb_func, p_context);
37417f65170SRuslan Bukin 
37517f65170SRuslan Bukin             err = m_default_mapper->AddAccessor(p_accessor,0);
37617f65170SRuslan Bukin         }
37717f65170SRuslan Bukin         else
378*fc502085SRuslan Bukin             err = OCSD_ERR_MEM;    // wrong type of object - treat as mem error
379*fc502085SRuslan Bukin 
380*fc502085SRuslan Bukin         if(err != OCSD_OK)
381*fc502085SRuslan Bukin             TrcMemAccFactory::DestroyAccessor(p_accessor);
382*fc502085SRuslan Bukin     }
383*fc502085SRuslan Bukin     return err;
384*fc502085SRuslan Bukin }
385*fc502085SRuslan Bukin 
addCallbackMemAcc(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)386*fc502085SRuslan Bukin ocsd_err_t DecodeTree::addCallbackMemAcc(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)
387*fc502085SRuslan Bukin {
38817f65170SRuslan Bukin     return initCallbackMemAcc(st_address, en_address, mem_space, (void *)p_cb_func, false, p_context);
38917f65170SRuslan Bukin }
39017f65170SRuslan Bukin 
addCallbackIDMemAcc(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)39117f65170SRuslan Bukin ocsd_err_t DecodeTree::addCallbackIDMemAcc(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)
39217f65170SRuslan Bukin {
39317f65170SRuslan Bukin     return initCallbackMemAcc(st_address, en_address, mem_space, (void *)p_cb_func, true, p_context);
39417f65170SRuslan Bukin }
39517f65170SRuslan Bukin 
removeMemAccByAddress(const ocsd_vaddr_t address,const ocsd_mem_space_acc_t mem_space)39617f65170SRuslan Bukin ocsd_err_t DecodeTree::removeMemAccByAddress(const ocsd_vaddr_t address, const ocsd_mem_space_acc_t mem_space)
39717f65170SRuslan Bukin {
39817f65170SRuslan Bukin     if(!hasMemAccMapper())
39917f65170SRuslan Bukin         return OCSD_ERR_NOT_INIT;
40017f65170SRuslan Bukin     return m_default_mapper->RemoveAccessorByAddress(address,mem_space,0);
40117f65170SRuslan Bukin }
40217f65170SRuslan Bukin 
createDecoder(const std::string & decoderName,const int createFlags,const CSConfig * pConfig)40317f65170SRuslan Bukin ocsd_err_t DecodeTree::createDecoder(const std::string &decoderName, const int createFlags, const CSConfig *pConfig)
40417f65170SRuslan Bukin {
40517f65170SRuslan Bukin     ocsd_err_t err = OCSD_OK;
40617f65170SRuslan Bukin     IDecoderMngr *pDecoderMngr = 0;
40717f65170SRuslan Bukin     TraceComponent *pTraceComp = 0;
40817f65170SRuslan Bukin     int crtFlags = createFlags;
40917f65170SRuslan Bukin 
41017f65170SRuslan Bukin     uint8_t CSID = 0;   // default for single stream decoder (no deformatter) - we ignore the ID
41117f65170SRuslan Bukin     if(usingFormatter())
41217f65170SRuslan Bukin     {
41317f65170SRuslan Bukin         CSID = pConfig->getTraceID();
41417f65170SRuslan Bukin         crtFlags |= OCSD_CREATE_FLG_INST_ID;
41517f65170SRuslan Bukin     }
41617f65170SRuslan Bukin 
41717f65170SRuslan Bukin     // create the decode element to attach to the channel.
41817f65170SRuslan Bukin     if((err = createDecodeElement(CSID)) != OCSD_OK)
41917f65170SRuslan Bukin         return err;
42017f65170SRuslan Bukin 
42117f65170SRuslan Bukin     // get the libary decoder register.
42217f65170SRuslan Bukin     OcsdLibDcdRegister * lib_reg = OcsdLibDcdRegister::getDecoderRegister();
42317f65170SRuslan Bukin     if(lib_reg == 0)
42417f65170SRuslan Bukin         return OCSD_ERR_NOT_INIT;
42517f65170SRuslan Bukin 
42617f65170SRuslan Bukin     // find the named decoder
42717f65170SRuslan Bukin     if((err = lib_reg->getDecoderMngrByName(decoderName,&pDecoderMngr)) != OCSD_OK)
42817f65170SRuslan Bukin         return err;
42917f65170SRuslan Bukin 
43017f65170SRuslan Bukin     // got the decoder...
43117f65170SRuslan Bukin     if((err = pDecoderMngr->createDecoder(crtFlags,(int)CSID,pConfig,&pTraceComp)) != OCSD_OK)
43217f65170SRuslan Bukin         return err;
43317f65170SRuslan Bukin 
43417f65170SRuslan Bukin     m_decode_elements[CSID]->SetDecoderElement(decoderName, pDecoderMngr, pTraceComp, true);
43517f65170SRuslan Bukin 
43617f65170SRuslan Bukin     // always attach an error logger
43717f65170SRuslan Bukin     if(err == OCSD_OK)
43817f65170SRuslan Bukin         err = pDecoderMngr->attachErrorLogger(pTraceComp,DecodeTree::s_i_error_logger);
43917f65170SRuslan Bukin 
44017f65170SRuslan Bukin     // if we created a packet decoder it may need additional components.
44117f65170SRuslan Bukin     if(crtFlags &  OCSD_CREATE_FLG_FULL_DECODER)
44217f65170SRuslan Bukin     {
44317f65170SRuslan Bukin         if(m_i_instr_decode && (err == OCSD_OK))
44417f65170SRuslan Bukin             err = pDecoderMngr->attachInstrDecoder(pTraceComp,m_i_instr_decode);
44517f65170SRuslan Bukin 
44617f65170SRuslan Bukin         if(err == OCSD_ERR_DCD_INTERFACE_UNUSED)    // ignore if instruction decoder refused
44717f65170SRuslan Bukin             err = OCSD_OK;
44817f65170SRuslan Bukin 
44917f65170SRuslan Bukin         if(m_i_mem_access && (err == OCSD_OK))
45017f65170SRuslan Bukin             err = pDecoderMngr->attachMemAccessor(pTraceComp,m_i_mem_access);
45117f65170SRuslan Bukin 
45217f65170SRuslan Bukin         if(err == OCSD_ERR_DCD_INTERFACE_UNUSED)    // ignore if mem accessor refused
45317f65170SRuslan Bukin             err = OCSD_OK;
45417f65170SRuslan Bukin 
45517f65170SRuslan Bukin         if( m_i_gen_elem_out && (err == OCSD_OK))
45617f65170SRuslan Bukin             err = pDecoderMngr->attachOutputSink(pTraceComp,m_i_gen_elem_out);
45717f65170SRuslan Bukin     }
45817f65170SRuslan Bukin 
45917f65170SRuslan Bukin     // finally attach the packet processor input to the demux output channel
46017f65170SRuslan Bukin     if(err == OCSD_OK)
46117f65170SRuslan Bukin     {
46217f65170SRuslan Bukin         ITrcDataIn *pDataIn = 0;
46317f65170SRuslan Bukin         if((err = pDecoderMngr->getDataInputI(pTraceComp,&pDataIn)) == OCSD_OK)
46417f65170SRuslan Bukin         {
46517f65170SRuslan Bukin             // got the interface -> attach to demux, or direct to input of decode tree
46617f65170SRuslan Bukin             if(usingFormatter())
46717f65170SRuslan Bukin                 err = m_frame_deformatter_root->getIDStreamAttachPt(CSID)->attach(pDataIn);
46817f65170SRuslan Bukin             else
46917f65170SRuslan Bukin                 m_i_decoder_root = pDataIn;
47017f65170SRuslan Bukin         }
47117f65170SRuslan Bukin     }
47217f65170SRuslan Bukin 
47317f65170SRuslan Bukin     if(err != OCSD_OK)
47417f65170SRuslan Bukin     {
47517f65170SRuslan Bukin         destroyDecodeElement(CSID); // will destroy decoder as well.
47617f65170SRuslan Bukin     }
47717f65170SRuslan Bukin     return err;
47817f65170SRuslan Bukin }
47917f65170SRuslan Bukin 
removeDecoder(const uint8_t CSID)48017f65170SRuslan Bukin ocsd_err_t DecodeTree::removeDecoder(const uint8_t CSID)
48117f65170SRuslan Bukin {
48217f65170SRuslan Bukin     ocsd_err_t err = OCSD_OK;
48317f65170SRuslan Bukin     uint8_t localID = CSID;
48417f65170SRuslan Bukin     if(!usingFormatter())
48517f65170SRuslan Bukin         localID = 0;
48617f65170SRuslan Bukin 
48717f65170SRuslan Bukin     if(usingFormatter() && !OCSD_IS_VALID_CS_SRC_ID(CSID))
48817f65170SRuslan Bukin         err = OCSD_ERR_INVALID_ID;
48917f65170SRuslan Bukin     else
49017f65170SRuslan Bukin     {
49117f65170SRuslan Bukin         destroyDecodeElement(localID);
49217f65170SRuslan Bukin     }
49317f65170SRuslan Bukin     return err;
49417f65170SRuslan Bukin }
49517f65170SRuslan Bukin 
getDecoderStats(const uint8_t CSID,ocsd_decode_stats_t ** p_stats_block)49617f65170SRuslan Bukin ocsd_err_t DecodeTree::getDecoderStats(const uint8_t CSID, ocsd_decode_stats_t **p_stats_block)
49717f65170SRuslan Bukin {
49817f65170SRuslan Bukin     ocsd_err_t err = OCSD_OK;
49917f65170SRuslan Bukin     TrcPktProcI *pPktProc = getPktProcI(CSID);
50017f65170SRuslan Bukin     if (!pPktProc)
50117f65170SRuslan Bukin         return OCSD_ERR_INVALID_PARAM_VAL;
50217f65170SRuslan Bukin     err = pPktProc->getStatsBlock(p_stats_block);
50317f65170SRuslan Bukin     if (err == OCSD_OK) {
50417f65170SRuslan Bukin         // copy in the global demux stats.
50517f65170SRuslan Bukin         (*p_stats_block)->demux.frame_bytes = m_demux_stats.frame_bytes;
50617f65170SRuslan Bukin         (*p_stats_block)->demux.no_id_bytes = m_demux_stats.no_id_bytes;
50717f65170SRuslan Bukin         (*p_stats_block)->demux.valid_id_bytes = m_demux_stats.valid_id_bytes;
50817f65170SRuslan Bukin         (*p_stats_block)->demux.unknown_id_bytes = m_demux_stats.unknown_id_bytes;
50917f65170SRuslan Bukin         (*p_stats_block)->demux.reserved_id_bytes = m_demux_stats.reserved_id_bytes;
51017f65170SRuslan Bukin     }
51117f65170SRuslan Bukin     return err;
51217f65170SRuslan Bukin }
51317f65170SRuslan Bukin 
resetDecoderStats(const uint8_t CSID)51417f65170SRuslan Bukin ocsd_err_t DecodeTree::resetDecoderStats(const uint8_t CSID)
51517f65170SRuslan Bukin {
51617f65170SRuslan Bukin     TrcPktProcI *pPktProc = getPktProcI(CSID);
51717f65170SRuslan Bukin     if (!pPktProc)
51817f65170SRuslan Bukin         return OCSD_ERR_INVALID_PARAM_VAL;
51917f65170SRuslan Bukin     pPktProc->resetStats();
52017f65170SRuslan Bukin 
52117f65170SRuslan Bukin     // reset the global demux stats.
52217f65170SRuslan Bukin     m_demux_stats.frame_bytes = 0;
52317f65170SRuslan Bukin     m_demux_stats.no_id_bytes = 0;
52417f65170SRuslan Bukin     m_demux_stats.valid_id_bytes = 0;
52517f65170SRuslan Bukin     m_demux_stats.unknown_id_bytes = 0;
52617f65170SRuslan Bukin     m_demux_stats.reserved_id_bytes = 0;
52717f65170SRuslan Bukin     return OCSD_OK;
52817f65170SRuslan Bukin }
52917f65170SRuslan Bukin 
getPktProcI(const uint8_t CSID)53017f65170SRuslan Bukin TrcPktProcI *DecodeTree::getPktProcI(const uint8_t CSID)
53117f65170SRuslan Bukin {
53217f65170SRuslan Bukin     TrcPktProcI *pPktProc = 0;
53317f65170SRuslan Bukin     TraceComponent *pComp, *pAssoc;
53417f65170SRuslan Bukin     DecodeTreeElement *pElem = getDecoderElement(CSID);
53517f65170SRuslan Bukin 
53617f65170SRuslan Bukin     if (pElem)
53717f65170SRuslan Bukin     {
53817f65170SRuslan Bukin         pComp = pElem->getDecoderHandle();
53917f65170SRuslan Bukin         if (pComp)
54017f65170SRuslan Bukin         {
54117f65170SRuslan Bukin             /* if this is a full decoder then the associated component is the packet processor */
54217f65170SRuslan Bukin             pAssoc = pComp->getAssocComponent();
54317f65170SRuslan Bukin             if (pAssoc)
54417f65170SRuslan Bukin                 pPktProc = dynamic_cast<TrcPktProcI *>(pAssoc);
54517f65170SRuslan Bukin             else
54617f65170SRuslan Bukin                 pPktProc = dynamic_cast<TrcPktProcI *>(pComp);
54717f65170SRuslan Bukin         }
54817f65170SRuslan Bukin     }
54917f65170SRuslan Bukin     return pPktProc;
55017f65170SRuslan Bukin }
55117f65170SRuslan Bukin 
getDecoderElement(const uint8_t CSID) const55217f65170SRuslan Bukin DecodeTreeElement * DecodeTree::getDecoderElement(const uint8_t CSID) const
55317f65170SRuslan Bukin {
55417f65170SRuslan Bukin     DecodeTreeElement *ret_elem = 0;
55517f65170SRuslan Bukin     if(usingFormatter() && OCSD_IS_VALID_CS_SRC_ID(CSID))
55617f65170SRuslan Bukin     {
55717f65170SRuslan Bukin         ret_elem = m_decode_elements[CSID];
55817f65170SRuslan Bukin     }
55917f65170SRuslan Bukin     else
56017f65170SRuslan Bukin         ret_elem = m_decode_elements[0];    // ID 0 is used if single leaf tree.
56117f65170SRuslan Bukin     return ret_elem;
56217f65170SRuslan Bukin }
56317f65170SRuslan Bukin 
getFirstElement(uint8_t & elemID)56417f65170SRuslan Bukin DecodeTreeElement *DecodeTree::getFirstElement(uint8_t &elemID)
56517f65170SRuslan Bukin {
56617f65170SRuslan Bukin     m_decode_elem_iter = 0;
56717f65170SRuslan Bukin     return getNextElement(elemID);
56817f65170SRuslan Bukin }
56917f65170SRuslan Bukin 
getNextElement(uint8_t & elemID)57017f65170SRuslan Bukin DecodeTreeElement *DecodeTree::getNextElement(uint8_t &elemID)
57117f65170SRuslan Bukin {
57217f65170SRuslan Bukin     DecodeTreeElement *ret_elem = 0;
57317f65170SRuslan Bukin 
57417f65170SRuslan Bukin     if(m_decode_elem_iter < 0x80)
57517f65170SRuslan Bukin     {
57617f65170SRuslan Bukin         // find a none zero entry or end of range
57717f65170SRuslan Bukin         while((m_decode_elem_iter < 0x80) && (m_decode_elements[m_decode_elem_iter] == 0))
57817f65170SRuslan Bukin             m_decode_elem_iter++;
57917f65170SRuslan Bukin 
58017f65170SRuslan Bukin         // return entry unless end of range
58117f65170SRuslan Bukin         if(m_decode_elem_iter < 0x80)
58217f65170SRuslan Bukin         {
58317f65170SRuslan Bukin             ret_elem = m_decode_elements[m_decode_elem_iter];
58417f65170SRuslan Bukin             elemID = m_decode_elem_iter;
58517f65170SRuslan Bukin             m_decode_elem_iter++;
58617f65170SRuslan Bukin         }
58717f65170SRuslan Bukin     }
58817f65170SRuslan Bukin     return ret_elem;
58917f65170SRuslan Bukin }
59017f65170SRuslan Bukin 
initialise(const ocsd_dcd_tree_src_t type,uint32_t formatterCfgFlags)59117f65170SRuslan Bukin bool DecodeTree::initialise(const ocsd_dcd_tree_src_t type, uint32_t formatterCfgFlags)
59217f65170SRuslan Bukin {
59317f65170SRuslan Bukin     ocsd_err_t err;
59417f65170SRuslan Bukin     m_dcd_tree_type = type;
59517f65170SRuslan Bukin     if(type ==  OCSD_TRC_SRC_FRAME_FORMATTED)
59617f65170SRuslan Bukin     {
59717f65170SRuslan Bukin         // frame formatted - we want to create the deformatter and hook it up
59817f65170SRuslan Bukin         m_frame_deformatter_root = new (std::nothrow) TraceFormatterFrameDecoder();
59917f65170SRuslan Bukin         if(m_frame_deformatter_root)
60017f65170SRuslan Bukin         {
60117f65170SRuslan Bukin             if (m_frame_deformatter_root->Init() != OCSD_OK)
60217f65170SRuslan Bukin                 return false;
60317f65170SRuslan Bukin             m_frame_deformatter_root->getErrLogAttachPt()->attach(DecodeTree::s_i_error_logger);
60417f65170SRuslan Bukin             err = m_frame_deformatter_root->Configure(formatterCfgFlags);
60517f65170SRuslan Bukin             if (err != OCSD_OK)
60617f65170SRuslan Bukin                 return false;
60717f65170SRuslan Bukin             m_i_decoder_root = dynamic_cast<ITrcDataIn*>(m_frame_deformatter_root);
60817f65170SRuslan Bukin             m_frame_deformatter_root->SetDemuxStatsBlock(&m_demux_stats);
60917f65170SRuslan Bukin         }
61017f65170SRuslan Bukin         else
61117f65170SRuslan Bukin             return false;
61217f65170SRuslan Bukin     }
61317f65170SRuslan Bukin     return true;
61417f65170SRuslan Bukin }
61517f65170SRuslan Bukin 
setSingleRoot(TrcPktProcI * pComp)61617f65170SRuslan Bukin void DecodeTree::setSingleRoot(TrcPktProcI *pComp)
61717f65170SRuslan Bukin {
61817f65170SRuslan Bukin     m_i_decoder_root = static_cast<ITrcDataIn*>(pComp);
61917f65170SRuslan Bukin }
62017f65170SRuslan Bukin 
createDecodeElement(const uint8_t CSID)62117f65170SRuslan Bukin ocsd_err_t DecodeTree::createDecodeElement(const uint8_t CSID)
62217f65170SRuslan Bukin {
62317f65170SRuslan Bukin     ocsd_err_t err = OCSD_ERR_INVALID_ID;
62417f65170SRuslan Bukin     if(CSID < 0x80)
62517f65170SRuslan Bukin     {
62617f65170SRuslan Bukin         if(m_decode_elements[CSID] == 0)
62717f65170SRuslan Bukin         {
62817f65170SRuslan Bukin             m_decode_elements[CSID] = new (std::nothrow) DecodeTreeElement();
62917f65170SRuslan Bukin             if(m_decode_elements[CSID] == 0)
63017f65170SRuslan Bukin                 err = OCSD_ERR_MEM;
63117f65170SRuslan Bukin             else
63217f65170SRuslan Bukin                 err = OCSD_OK;
63317f65170SRuslan Bukin         }
63417f65170SRuslan Bukin         else
63517f65170SRuslan Bukin             err = OCSD_ERR_ATTACH_TOO_MANY;
63617f65170SRuslan Bukin     }
63717f65170SRuslan Bukin     return err;
63817f65170SRuslan Bukin }
63917f65170SRuslan Bukin 
destroyDecodeElement(const uint8_t CSID)64017f65170SRuslan Bukin void DecodeTree::destroyDecodeElement(const uint8_t CSID)
64117f65170SRuslan Bukin {
64217f65170SRuslan Bukin     if(CSID < 0x80)
64317f65170SRuslan Bukin     {
64417f65170SRuslan Bukin         if(m_decode_elements[CSID] != 0)
64517f65170SRuslan Bukin         {
64617f65170SRuslan Bukin             m_decode_elements[CSID]->DestroyElem();
64717f65170SRuslan Bukin             delete m_decode_elements[CSID];
64817f65170SRuslan Bukin             m_decode_elements[CSID] = 0;
64917f65170SRuslan Bukin         }
65017f65170SRuslan Bukin     }
65117f65170SRuslan Bukin }
65217f65170SRuslan Bukin 
setIDFilter(std::vector<uint8_t> & ids)65317f65170SRuslan Bukin ocsd_err_t DecodeTree::setIDFilter(std::vector<uint8_t> &ids)
65417f65170SRuslan Bukin {
65517f65170SRuslan Bukin     ocsd_err_t err = OCSD_ERR_DCDT_NO_FORMATTER;
65617f65170SRuslan Bukin     if(usingFormatter())
65717f65170SRuslan Bukin     {
65817f65170SRuslan Bukin         err = m_frame_deformatter_root->OutputFilterAllIDs(false);
65917f65170SRuslan Bukin         if(err == OCSD_OK)
66017f65170SRuslan Bukin             err = m_frame_deformatter_root->OutputFilterIDs(ids,true);
66117f65170SRuslan Bukin     }
66217f65170SRuslan Bukin     return err;
66317f65170SRuslan Bukin }
66417f65170SRuslan Bukin 
clearIDFilter()66517f65170SRuslan Bukin ocsd_err_t DecodeTree::clearIDFilter()
66617f65170SRuslan Bukin {
66717f65170SRuslan Bukin     ocsd_err_t err = OCSD_ERR_DCDT_NO_FORMATTER;
66817f65170SRuslan Bukin     if(usingFormatter())
66917f65170SRuslan Bukin     {
67017f65170SRuslan Bukin         err = m_frame_deformatter_root->OutputFilterAllIDs(true);
67117f65170SRuslan Bukin     }
67217f65170SRuslan Bukin     return err;
67317f65170SRuslan Bukin }
67417f65170SRuslan Bukin 
67517f65170SRuslan Bukin /** add a protocol packet printer */
addPacketPrinter(uint8_t CSID,bool bMonitor,ItemPrinter ** ppPrinter)67617f65170SRuslan Bukin ocsd_err_t DecodeTree::addPacketPrinter(uint8_t CSID, bool bMonitor, ItemPrinter **ppPrinter)
67717f65170SRuslan Bukin {
67817f65170SRuslan Bukin     ocsd_err_t err = OCSD_ERR_INVALID_PARAM_VAL;
67917f65170SRuslan Bukin     DecodeTreeElement *pElement = getDecoderElement(CSID);
68017f65170SRuslan Bukin     if (pElement)
68117f65170SRuslan Bukin     {
68217f65170SRuslan Bukin         ocsd_trace_protocol_t protocol = pElement->getProtocol();
68317f65170SRuslan Bukin         ItemPrinter *pPrinter;
68417f65170SRuslan Bukin 
68517f65170SRuslan Bukin         pPrinter = PktPrinterFact::createProtocolPrinter(getPrinterList(), protocol, CSID);
68617f65170SRuslan Bukin         if (pPrinter)
68717f65170SRuslan Bukin         {
68817f65170SRuslan Bukin             pPrinter->setMessageLogger(getCurrentErrorLogI()->getOutputLogger());
68917f65170SRuslan Bukin             switch (protocol)
69017f65170SRuslan Bukin             {
69117f65170SRuslan Bukin             case  OCSD_PROTOCOL_ETMV4I:
69217f65170SRuslan Bukin             case  OCSD_PROTOCOL_ETE:
69317f65170SRuslan Bukin             {
69417f65170SRuslan Bukin                 PacketPrinter<EtmV4ITrcPacket> *pTPrinter = dynamic_cast<PacketPrinter<EtmV4ITrcPacket> *>(pPrinter);
69517f65170SRuslan Bukin                 if (bMonitor)
69617f65170SRuslan Bukin                     err = pElement->getDecoderMngr()->attachPktMonitor(pElement->getDecoderHandle(), (IPktRawDataMon<EtmV4ITrcPacket> *)pTPrinter);
69717f65170SRuslan Bukin                 else
69817f65170SRuslan Bukin                     err = pElement->getDecoderMngr()->attachPktSink(pElement->getDecoderHandle(), (IPktDataIn<EtmV4ITrcPacket> *)pTPrinter);
69917f65170SRuslan Bukin             }
70017f65170SRuslan Bukin             break;
70117f65170SRuslan Bukin 
70217f65170SRuslan Bukin             case  OCSD_PROTOCOL_ETMV3:
70317f65170SRuslan Bukin             {
70417f65170SRuslan Bukin                 PacketPrinter<EtmV3TrcPacket> *pTPrinter = dynamic_cast<PacketPrinter<EtmV3TrcPacket> *>(pPrinter);
70517f65170SRuslan Bukin                 if (bMonitor)
70617f65170SRuslan Bukin                     err = pElement->getDecoderMngr()->attachPktMonitor(pElement->getDecoderHandle(), (IPktRawDataMon<EtmV3TrcPacket> *)pTPrinter);
70717f65170SRuslan Bukin                 else
70817f65170SRuslan Bukin                     err = pElement->getDecoderMngr()->attachPktSink(pElement->getDecoderHandle(), (IPktDataIn<EtmV3TrcPacket> *)pTPrinter);
70917f65170SRuslan Bukin             }
71017f65170SRuslan Bukin             break;
71117f65170SRuslan Bukin 
71217f65170SRuslan Bukin             case  OCSD_PROTOCOL_PTM:
71317f65170SRuslan Bukin             {
71417f65170SRuslan Bukin                 PacketPrinter<PtmTrcPacket> *pTPrinter = dynamic_cast<PacketPrinter<PtmTrcPacket> *>(pPrinter);
71517f65170SRuslan Bukin                 if (bMonitor)
716                     err = pElement->getDecoderMngr()->attachPktMonitor(pElement->getDecoderHandle(), (IPktRawDataMon<PtmTrcPacket> *)pTPrinter);
717                 else
718                     err = pElement->getDecoderMngr()->attachPktSink(pElement->getDecoderHandle(), (IPktDataIn<PtmTrcPacket> *)pTPrinter);
719             }
720             break;
721 
722             case OCSD_PROTOCOL_STM:
723             {
724                 PacketPrinter<StmTrcPacket> *pTPrinter = dynamic_cast<PacketPrinter<StmTrcPacket> *>(pPrinter);
725                 if (bMonitor)
726                     err = pElement->getDecoderMngr()->attachPktMonitor(pElement->getDecoderHandle(), (IPktRawDataMon<StmTrcPacket> *)pTPrinter);
727                 else
728                     err = pElement->getDecoderMngr()->attachPktSink(pElement->getDecoderHandle(), (IPktDataIn<StmTrcPacket> *)pTPrinter);
729             }
730             break;
731 
732             default:
733                 err = OCSD_ERR_NO_PROTOCOL;
734                 break;
735             }
736 
737             if (err == OCSD_OK)
738             {
739                 if (ppPrinter)
740                     *ppPrinter = pPrinter;
741             }
742             else
743                 PktPrinterFact::destroyPrinter(getPrinterList(), pPrinter);
744         }
745     }
746     return err;
747 }
748 
749 /** add a raw frame printer */
addRawFramePrinter(RawFramePrinter ** ppPrinter,uint32_t flags)750 ocsd_err_t DecodeTree::addRawFramePrinter(RawFramePrinter **ppPrinter, uint32_t flags)
751 {
752     ocsd_err_t err = OCSD_ERR_MEM;
753     RawFramePrinter *pPrinter = PktPrinterFact::createRawFramePrinter(getPrinterList());
754     if (pPrinter)
755     {
756         pPrinter->setMessageLogger((DecodeTree::getCurrentErrorLogI()->getOutputLogger()));
757         TraceFormatterFrameDecoder *pFrameDecoder = getFrameDeformatter();
758         uint32_t cfgFlags = pFrameDecoder->getConfigFlags();
759         cfgFlags |= ((uint32_t)flags & (OCSD_DFRMTR_PACKED_RAW_OUT | OCSD_DFRMTR_UNPACKED_RAW_OUT));
760         pFrameDecoder->Configure(cfgFlags);
761         err = pFrameDecoder->getTrcRawFrameAttachPt()->attach(pPrinter);
762         if (ppPrinter && (err==OCSD_OK))
763             *ppPrinter = pPrinter;
764     }
765     return err;
766 }
767 
768 /** add a generic element output printer */
addGenElemPrinter(TrcGenericElementPrinter ** ppPrinter)769 ocsd_err_t DecodeTree::addGenElemPrinter(TrcGenericElementPrinter **ppPrinter)
770 {
771     ocsd_err_t err = OCSD_ERR_MEM;
772     TrcGenericElementPrinter *pPrinter = PktPrinterFact::createGenElemPrinter(getPrinterList());
773     if (pPrinter)
774     {
775         pPrinter->setMessageLogger((DecodeTree::getCurrentErrorLogI()->getOutputLogger()));
776         setGenTraceElemOutI(pPrinter);
777         err = OCSD_OK;
778         if (ppPrinter)
779             *ppPrinter = pPrinter;
780     }
781     return err;
782 
783 }
784 
785 /* End of File ocsd_dcd_tree.cpp */
786