xref: /aosp_15_r20/external/OpenCSD/decoder/tests/snapshot_parser_lib/source/ss_to_dcdtree.cpp (revision 02ca8ccacfba7e0df68f3332a95f3180334d6649)
1 /*
2  * \file       ss_to_dcdtree.cpp
3  * \brief      OpenCSD :
4  *
5  * \copyright  Copyright (c) 2015, ARM Limited. All Rights Reserved.
6  */
7 
8 /*
9  * Redistribution and use in source and binary forms, with or without modification,
10  * are permitted provided that the following conditions are met:
11  *
12  * 1. Redistributions of source code must retain the above copyright notice,
13  * this list of conditions and the following disclaimer.
14  *
15  * 2. Redistributions in binary form must reproduce the above copyright notice,
16  * this list of conditions and the following disclaimer in the documentation
17  * and/or other materials provided with the distribution.
18  *
19  * 3. Neither the name of the copyright holder nor the names of its contributors
20  * may be used to endorse or promote products derived from this software without
21  * specific prior written permission.
22  *
23  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND
24  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
25  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
26  * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
27  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
28  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
29  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
30  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
31  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
32  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
33  */
34 
35 #include "ss_to_dcdtree.h"
36 #include "ss_key_value_names.h"
37 
38 
CreateDcdTreeFromSnapShot()39 CreateDcdTreeFromSnapShot::CreateDcdTreeFromSnapShot() :
40     m_bInit(false),
41     m_pDecodeTree(0),
42     m_pReader(0),
43     m_pErrLogInterface(0),
44     m_bPacketProcOnly(false),
45     m_BufferFileName("")
46 {
47     m_errlog_handle = 0;
48     m_add_create_flags = 0;
49 }
50 
~CreateDcdTreeFromSnapShot()51 CreateDcdTreeFromSnapShot::~CreateDcdTreeFromSnapShot()
52 {
53     destroyDecodeTree();
54 }
55 
initialise(SnapShotReader * pReader,ITraceErrorLog * pErrLogInterface)56 void CreateDcdTreeFromSnapShot::initialise(SnapShotReader *pReader, ITraceErrorLog *pErrLogInterface)
57 {
58     if((pErrLogInterface != 0) && (pReader != 0))
59     {
60         m_pReader = pReader;
61         m_pErrLogInterface = pErrLogInterface;
62         m_errlog_handle = m_pErrLogInterface->RegisterErrorSource("ss2_dcdtree");
63         m_bInit = true;
64     }
65 }
66 
getBufferFileNameFromBuffName(const std::string & buff_name)67 std::string CreateDcdTreeFromSnapShot::getBufferFileNameFromBuffName(const std::string& buff_name)
68 {
69     Parser::TraceBufferSourceTree tree;
70     std::string buffFileName = "";
71 
72     if (m_pReader->getTraceBufferSourceTree(buff_name, tree))
73     {
74         buffFileName = m_pReader->getSnapShotDir() + tree.buffer_info.dataFileName;
75     }
76     return buffFileName;
77 }
78 
79 
createDecodeTree(const std::string & SourceName,bool bPacketProcOnly,uint32_t add_create_flags)80 bool CreateDcdTreeFromSnapShot::createDecodeTree(const std::string &SourceName, bool bPacketProcOnly, uint32_t add_create_flags)
81 {
82     ocsd_err_t err = OCSD_OK;
83 
84     m_add_create_flags = add_create_flags;
85     if(m_bInit)
86     {
87         if(!m_pReader->snapshotReadOK())
88         {
89             LogError("Supplied snapshot reader has not correctly read the snapshot.\n");
90             return false;
91         }
92 
93         m_bPacketProcOnly = bPacketProcOnly;
94         Parser::TraceBufferSourceTree tree;
95 
96         if(m_pReader->getTraceBufferSourceTree(SourceName, tree))
97         {
98             int numDecodersCreated = 0; // count how many we create - if none then give up.
99             uint32_t formatter_flags = OCSD_DFRMTR_FRAME_MEM_ALIGN;
100 
101             /* make a note of the trace binary file name + path to ss directory */
102             m_BufferFileName = m_pReader->getSnapShotDir() + tree.buffer_info.dataFileName;
103 
104             ocsd_dcd_tree_src_t src_format = tree.buffer_info.dataFormat == "source_data" ? OCSD_TRC_SRC_SINGLE : OCSD_TRC_SRC_FRAME_FORMATTED;
105 
106             if (tree.buffer_info.dataFormat == "dstream_coresight")
107                 formatter_flags = OCSD_DFRMTR_HAS_FSYNCS;
108 
109             /* create the initial device tree */
110             // TBD:     handle syncs / hsyncs data from TPIU
111             m_pDecodeTree = DecodeTree::CreateDecodeTree(src_format, formatter_flags);
112             if(m_pDecodeTree == 0)
113             {
114                 LogError("Failed to create decode tree object\n");
115                 return false;
116             }
117 
118             // use our error logger - don't use the tree default.
119             m_pDecodeTree->setAlternateErrorLogger(m_pErrLogInterface);
120 
121             if(!bPacketProcOnly)
122             {
123                 m_pDecodeTree->createMemAccMapper();
124             }
125 
126             /* run through each protocol source to this buffer... */
127             std::map<std::string, std::string>::iterator it = tree.source_core_assoc.begin();
128 
129             while(it != tree.source_core_assoc.end())
130             {
131                 Parser::Parsed *etm_dev, *core_dev;
132                 if(m_pReader->getDeviceData(it->first,&etm_dev))
133                 {
134                     // found the device data for this device.
135 
136                     // see if we have a core name (STM / ITM not associated with a core);
137                     std::string coreDevName = it->second;
138                     if(coreDevName.size() > 0)
139                     {
140                         if(m_pReader->getDeviceData(coreDevName,&core_dev))
141                         {
142                             if(createPEDecoder(core_dev->deviceTypeName,etm_dev))
143                             {
144                                 numDecodersCreated++;
145                                 if(!bPacketProcOnly &&(core_dev->dumpDefs.size() > 0))
146                                 {
147                                     err = processDumpfiles(core_dev->dumpDefs);
148                                 }
149                             }
150                             else
151                             {
152                                 std::ostringstream oss;
153                                 oss << "Failed to create decoder for source " << it->first << ".\n";
154                                 LogError(oss.str());
155                             }
156                         }
157                         else
158                         {
159                             // Could not find the device data for the core.
160                             // unexpected - since we created the associations.
161                             std::ostringstream oss;
162                             oss << "Failed to get device data for source " << it->first << ".\n";
163                             LogError(oss.str());
164                         }
165                     }
166                     else
167                     {
168                         // none-core source
169                         if(createSTDecoder(etm_dev))
170                         {
171                              numDecodersCreated++;
172                         }
173                         else
174                         {
175                             std::ostringstream oss;
176                             oss << "Failed to create decoder for none core source " << it->first << ".\n";
177                             LogError(oss.str());
178                         }
179                     }
180                 }
181                 else
182                 {
183                     // TBD: could not find the device data for the source.
184                     // again unexpected - suggests ss format error.
185                     std::ostringstream oss;
186                     oss << "Failed to find device data for source " << it->first << ".\n";
187                     LogError(oss.str());
188                 }
189                 if(src_format == OCSD_TRC_SRC_SINGLE)
190                     it = tree.source_core_assoc.end();
191                 else
192                     it++;
193             }
194 
195             if((numDecodersCreated == 0) || (err != OCSD_OK))
196             {
197                 // nothing useful found
198                 destroyDecodeTree();
199             }
200         }
201         else
202         {
203             std::ostringstream oss;
204             oss << "Failed to get parsed source tree for buffer " << SourceName << ".\n";
205             LogError(oss.str());
206         }
207     }
208     return (bool)(m_pDecodeTree != 0);
209 }
210 
destroyDecodeTree()211 void CreateDcdTreeFromSnapShot::destroyDecodeTree()
212 {
213     if(m_pDecodeTree)
214         DecodeTree::DestroyDecodeTree(m_pDecodeTree);
215     m_pDecodeTree = 0;
216     m_pReader = 0;
217     m_pErrLogInterface = 0;
218     m_errlog_handle = 0;
219     m_BufferFileName = "";
220 }
221 
LogError(const std::string & msg)222 void  CreateDcdTreeFromSnapShot::LogError(const std::string &msg)
223 {
224     ocsdError err(OCSD_ERR_SEV_ERROR,OCSD_ERR_TEST_SS_TO_DECODER,msg);
225     m_pErrLogInterface->LogError(m_errlog_handle,&err);
226 }
227 
LogError(const ocsdError & err)228 void CreateDcdTreeFromSnapShot::LogError(const ocsdError &err)
229 {
230     m_pErrLogInterface->LogError(m_errlog_handle,&err);
231 }
232 
createPEDecoder(const std::string & coreName,Parser::Parsed * devSrc)233 bool CreateDcdTreeFromSnapShot::createPEDecoder(const std::string &coreName, Parser::Parsed *devSrc)
234 {
235     bool bCreatedDecoder = false;
236     std::string devTypeName = devSrc->deviceTypeName;
237 
238     // split off .x from type name.
239     std::string::size_type pos = devTypeName.find_first_of('.');
240     if(pos != std::string::npos)
241         devTypeName = devTypeName.substr(0,pos);
242 
243     // split according to protocol
244     if(devTypeName == ETMv4Protocol)
245     {
246         bCreatedDecoder = createETMv4Decoder(coreName,devSrc);
247     }
248     else if(devTypeName == ETMv3Protocol)
249     {
250         bCreatedDecoder = createETMv3Decoder(coreName,devSrc);
251     }
252     else if(devTypeName == PTMProtocol || devTypeName == PFTProtocol)
253     {
254         bCreatedDecoder = createPTMDecoder(coreName,devSrc);
255     }
256     else if (devTypeName == ETEProtocol)
257     {
258         bCreatedDecoder = createETEDecoder(coreName, devSrc);
259     }
260 
261     return bCreatedDecoder;
262 }
263 
264 // create an ETMv4 decoder based on the deviceN.ini file.
createETMv4Decoder(const std::string & coreName,Parser::Parsed * devSrc,const bool bDataChannel)265 bool CreateDcdTreeFromSnapShot::createETMv4Decoder(const std::string &coreName, Parser::Parsed *devSrc, const bool bDataChannel /* = false*/)
266 {
267     bool createdDecoder = false;
268     bool configOK = true;
269 
270     // generate the config data from the device data.
271     ocsd_etmv4_cfg config;
272 
273     regs_to_access_t regs_to_access[] = {
274         { ETMv4RegCfg, true, &config.reg_configr, 0 },
275         { ETMv4RegIDR, true, &config.reg_traceidr, 0 },
276         { ETMv4RegIDR0, true, &config.reg_idr0, 0 },
277         { ETMv4RegIDR1, false, &config.reg_idr1, 0x4100F403 },
278         { ETMv4RegIDR2, true, &config.reg_idr2, 0 },
279         { ETMv4RegIDR8, false, &config.reg_idr8, 0 },
280         { ETMv4RegIDR9, false, &config.reg_idr9, 0 },
281         { ETMv4RegIDR10, false, &config.reg_idr10, 0 },
282         { ETMv4RegIDR11, false, &config.reg_idr11, 0 },
283         { ETMv4RegIDR12, false, &config.reg_idr12, 0 },
284         { ETMv4RegIDR13,false, &config.reg_idr13, 0 },
285     };
286 
287     // extract registers
288     configOK = getRegisters(devSrc->regDefs,sizeof(regs_to_access)/sizeof(regs_to_access_t), regs_to_access);
289 
290     // extract core profile
291     if(configOK)
292         configOK = getCoreProfile(coreName,config.arch_ver,config.core_prof);
293 
294     // good config - generate the decoder on the tree.
295     if(configOK)
296     {
297         ocsd_err_t err = OCSD_OK;
298         EtmV4Config configObj(&config);
299         const char *decoderName = bDataChannel ? OCSD_BUILTIN_DCD_ETMV4D : OCSD_BUILTIN_DCD_ETMV4I;
300 
301         err = m_pDecodeTree->createDecoder(decoderName, m_add_create_flags | (m_bPacketProcOnly ? OCSD_CREATE_FLG_PACKET_PROC : OCSD_CREATE_FLG_FULL_DECODER),&configObj);
302 
303         if(err ==  OCSD_OK)
304             createdDecoder = true;
305         else
306         {
307             std::string msg = "Snapshot processor : failed to create " +  (std::string)decoderName + " decoder on decode tree.";
308             LogError(ocsdError(OCSD_ERR_SEV_ERROR,err,msg));
309         }
310     }
311 
312     return createdDecoder;
313 }
314 
createETEDecoder(const std::string & coreName,Parser::Parsed * devSrc)315 bool CreateDcdTreeFromSnapShot::createETEDecoder(const std::string &coreName, Parser::Parsed *devSrc)
316 {
317     bool createdDecoder = false;
318     bool configOK = true;
319 
320     // generate the config data from the device data.
321     ocsd_ete_cfg config;
322 
323     // ete regs are same names Etmv4 in places...
324     regs_to_access_t regs_to_access[] = {
325         { ETMv4RegCfg, true, &config.reg_configr, 0 },
326         { ETMv4RegIDR, true, &config.reg_traceidr, 0 },
327         { ETMv4RegIDR0, true, &config.reg_idr0, 0 },
328         { ETMv4RegIDR1, false, &config.reg_idr1, 0x4100F403 },
329         { ETMv4RegIDR2, true, &config.reg_idr2, 0 },
330         { ETMv4RegIDR8, false, &config.reg_idr8, 0 },
331         { ETERegDevArch, false, &config.reg_devarch, 0x47705A13 },
332     };
333 
334     // extract registers
335     configOK = getRegisters(devSrc->regDefs, sizeof(regs_to_access) / sizeof(regs_to_access_t), regs_to_access);
336 
337     // extract core profile
338     if (configOK)
339         configOK = getCoreProfile(coreName, config.arch_ver, config.core_prof);
340 
341     // good config - generate the decoder on the tree.
342     if (configOK)
343     {
344         ocsd_err_t err = OCSD_OK;
345         ETEConfig configObj(&config);
346         const char *decoderName = OCSD_BUILTIN_DCD_ETE;
347 
348         err = m_pDecodeTree->createDecoder(decoderName, m_add_create_flags | (m_bPacketProcOnly ? OCSD_CREATE_FLG_PACKET_PROC : OCSD_CREATE_FLG_FULL_DECODER), &configObj);
349 
350         if (err == OCSD_OK)
351             createdDecoder = true;
352         else
353         {
354             std::string msg = "Snapshot processor : failed to create " + (std::string)decoderName + " decoder on decode tree.";
355             LogError(ocsdError(OCSD_ERR_SEV_ERROR, err, msg));
356         }
357     }
358 
359     return createdDecoder;
360 }
361 
362 // create an ETMv3 decoder based on the register values in the deviceN.ini file.
createETMv3Decoder(const std::string & coreName,Parser::Parsed * devSrc)363 bool CreateDcdTreeFromSnapShot::createETMv3Decoder(const std::string &coreName, Parser::Parsed *devSrc)
364 {
365     bool createdDecoder = false;
366     bool configOK = true;
367 
368     // generate the config data from the device data.
369     ocsd_etmv3_cfg cfg_regs;
370 
371     regs_to_access_t regs_to_access[] = {
372         { ETMv3PTMRegIDR, true, &cfg_regs.reg_idr, 0 },
373         { ETMv3PTMRegCR, true, &cfg_regs.reg_ctrl, 0 },
374         { ETMv3PTMRegCCER, true, &cfg_regs.reg_ccer, 0 },
375         { ETMv3PTMRegTraceIDR, true, &cfg_regs.reg_trc_id, 0}
376     };
377 
378     // extract registers
379     configOK = getRegisters(devSrc->regDefs,sizeof(regs_to_access)/sizeof(regs_to_access_t), regs_to_access);
380 
381     // extract core profile
382     if(configOK)
383         configOK = getCoreProfile(coreName,cfg_regs.arch_ver,cfg_regs.core_prof);
384 
385     // good config - generate the decoder on the tree.
386     if(configOK)
387     {
388         EtmV3Config config(&cfg_regs);
389         ocsd_err_t err = OCSD_OK;
390         err = m_pDecodeTree->createDecoder(OCSD_BUILTIN_DCD_ETMV3, m_bPacketProcOnly ? OCSD_CREATE_FLG_PACKET_PROC : OCSD_CREATE_FLG_FULL_DECODER,&config);
391 
392         if(err ==  OCSD_OK)
393             createdDecoder = true;
394         else
395             LogError(ocsdError(OCSD_ERR_SEV_ERROR,err,"Snapshot processor : failed to create ETMV3 decoder on decode tree."));
396     }
397     return createdDecoder;
398 }
399 
createPTMDecoder(const std::string & coreName,Parser::Parsed * devSrc)400 bool CreateDcdTreeFromSnapShot::createPTMDecoder(const std::string &coreName, Parser::Parsed *devSrc)
401 {
402     bool createdDecoder = false;
403     bool configOK = true;
404 
405     // generate the config data from the device data.
406 
407     ocsd_ptm_cfg config;
408 
409     regs_to_access_t regs_to_access[] = {
410         { ETMv3PTMRegIDR, true, &config.reg_idr, 0 },
411         { ETMv3PTMRegCR, true, &config.reg_ctrl, 0 },
412         { ETMv3PTMRegCCER, true, &config.reg_ccer, 0 },
413         { ETMv3PTMRegTraceIDR, true, &config.reg_trc_id, 0}
414     };
415 
416     // extract registers
417     configOK = getRegisters(devSrc->regDefs,sizeof(regs_to_access)/sizeof(regs_to_access_t), regs_to_access);
418 
419     // extract core profile
420     if(configOK)
421         configOK = getCoreProfile(coreName,config.arch_ver,config.core_prof);
422 
423     // good config - generate the decoder on the tree.
424     if(configOK)
425     {
426         PtmConfig configObj(&config);
427         ocsd_err_t err = OCSD_OK;
428         err = m_pDecodeTree->createDecoder(OCSD_BUILTIN_DCD_PTM, m_bPacketProcOnly ? OCSD_CREATE_FLG_PACKET_PROC : OCSD_CREATE_FLG_FULL_DECODER,&configObj);
429 
430         if(err ==  OCSD_OK)
431             createdDecoder = true;
432         else
433             LogError(ocsdError(OCSD_ERR_SEV_ERROR,err,"Snapshot processor : failed to create PTM decoder on decode tree."));
434     }
435     return createdDecoder;
436 }
437 
createSTDecoder(Parser::Parsed * devSrc)438 bool CreateDcdTreeFromSnapShot::createSTDecoder(Parser::Parsed *devSrc)
439 {
440     bool bCreatedDecoder = false;
441     std::string devTypeName = devSrc->deviceTypeName;
442 
443     // split off .x from type name.
444     std::string::size_type pos = devTypeName.find_first_of('.');
445     if(pos != std::string::npos)
446         devTypeName = devTypeName.substr(0,pos);
447 
448     if(devTypeName == STMProtocol)
449     {
450         bCreatedDecoder = createSTMDecoder(devSrc);
451     }
452 
453     return bCreatedDecoder;
454 }
455 
createSTMDecoder(Parser::Parsed * devSrc)456 bool CreateDcdTreeFromSnapShot::createSTMDecoder(Parser::Parsed *devSrc)
457 {
458     bool createdDecoder = false;
459     bool configOK = true;
460 
461     // generate the config data from the device data.
462 
463     ocsd_stm_cfg config;
464 
465     regs_to_access_t regs_to_access[] = {
466         { STMRegTCSR, true, &config.reg_tcsr, 0 }
467     };
468 
469     configOK = getRegisters(devSrc->regDefs,sizeof(regs_to_access)/sizeof(regs_to_access_t), regs_to_access);
470     if(configOK)
471     {
472         ocsd_err_t err = OCSD_OK;
473         STMConfig configObj(&config);
474 
475         err = m_pDecodeTree->createDecoder(OCSD_BUILTIN_DCD_STM, m_bPacketProcOnly ? OCSD_CREATE_FLG_PACKET_PROC : OCSD_CREATE_FLG_FULL_DECODER,&configObj);
476 
477         if(err ==  OCSD_OK)
478             createdDecoder = true;
479         else
480             LogError(ocsdError(OCSD_ERR_SEV_ERROR,err,"Snapshot processor : failed to create STM decoder on decode tree."));
481     }
482 
483     return createdDecoder;
484 }
485 
486 
487 
488 // get a set of register values.
getRegisters(std::map<std::string,std::string,Util::CaseInsensitiveLess> & regDefs,int numRegs,regs_to_access_t * reg_access_array)489 bool CreateDcdTreeFromSnapShot::getRegisters(std::map<std::string, std::string, Util::CaseInsensitiveLess> &regDefs, int numRegs, regs_to_access_t *reg_access_array)
490 {
491     bool regsOK = true;
492 
493     for(int rv = 0; rv < numRegs; rv++)
494     {
495         if(!getRegByPrefix( regDefs,reg_access_array[rv]))
496             regsOK = false;
497     }
498     return regsOK;
499 }
500 
501 // strip out any parts with brackets
getRegByPrefix(std::map<std::string,std::string,Util::CaseInsensitiveLess> & regDefs,regs_to_access_t & reg_accessor)502 bool CreateDcdTreeFromSnapShot::getRegByPrefix(std::map<std::string, std::string, Util::CaseInsensitiveLess> &regDefs,
503     regs_to_access_t &reg_accessor)
504 {
505     std::ostringstream oss;
506     bool bFound = false;
507     std::map<std::string, std::string, Util::CaseInsensitiveLess>::iterator it;
508     std::string prefix_cmp;
509     std::string::size_type pos;
510     std::string strval;
511 
512     *reg_accessor.value = 0;
513 
514     it = regDefs.begin();
515     while((it != regDefs.end()) && !bFound)
516     {
517         prefix_cmp = it->first;
518         pos = prefix_cmp.find_first_of('(');
519         if(pos != std::string::npos)
520         {
521             prefix_cmp = prefix_cmp.substr(0, pos);
522         }
523         if(prefix_cmp == reg_accessor.pszName)
524         {
525             strval = it->second;
526             bFound = true;
527         }
528         it++;
529     }
530 
531     if(bFound)
532         *reg_accessor.value = strtoul(strval.c_str(),0,0);
533     else
534     {
535         ocsd_err_severity_t sev = OCSD_ERR_SEV_ERROR;
536         if(reg_accessor.failIfMissing)
537         {
538             oss << "Error:";
539         }
540         else
541         {
542             // no fail if missing - set any default and just warn.
543             bFound = true;
544             oss << "Warning: Default set for register. ";
545             sev = OCSD_ERR_SEV_WARN;
546             *reg_accessor.value = reg_accessor.val_default;
547         }
548         oss << "Missing " << reg_accessor.pszName << "\n";
549         m_pErrLogInterface->LogMessage(m_errlog_handle, sev, oss.str());
550     }
551     return bFound;
552 }
553 
getCoreProfile(const std::string & coreName,ocsd_arch_version_t & arch_ver,ocsd_core_profile_t & core_prof)554 bool CreateDcdTreeFromSnapShot::getCoreProfile(const std::string &coreName, ocsd_arch_version_t &arch_ver, ocsd_core_profile_t &core_prof)
555 {
556     bool profileOK = true;
557     ocsd_arch_profile_t ap = m_arch_profiles.getArchProfile(coreName);
558     if(ap.arch != ARCH_UNKNOWN)
559     {
560         arch_ver = ap.arch;
561         core_prof = ap.profile;
562     }
563     else
564     {
565         std::ostringstream oss;
566         oss << "Unrecognized Core name " << coreName << ". Cannot evaluate profile or architecture.";
567         LogError(oss.str());
568         profileOK = false;
569     }
570     return profileOK;
571 }
572 
573 typedef struct mem_space_keys {
574     const char* key_name;
575     ocsd_mem_space_acc_t memspace;
576 } mem_space_keys_t;
577 
578 static mem_space_keys_t space_map[] = {
579     /* single spaces */
580     { "EL1S", OCSD_MEM_SPACE_EL1S },
581     { "EL1N", OCSD_MEM_SPACE_EL1N },
582     { "EL1R", OCSD_MEM_SPACE_EL1R },
583     { "EL2S", OCSD_MEM_SPACE_EL2S },
584     { "EL2" , OCSD_MEM_SPACE_EL2 }, /* old EL2 NS name - prior to EL2S existing */
585     { "EL2N", OCSD_MEM_SPACE_EL2 },
586     { "EL2R", OCSD_MEM_SPACE_EL2R },
587     { "EL3" , OCSD_MEM_SPACE_EL3  },
588     { "ROOT", OCSD_MEM_SPACE_ROOT },
589     /* multiple memory spaces */
590     { "S"   , OCSD_MEM_SPACE_S},
591     { "N"   , OCSD_MEM_SPACE_N},
592     { "R"   , OCSD_MEM_SPACE_R},
593     { "ANY" , OCSD_MEM_SPACE_ANY},
594     /* older names - from spec but not expected to be used in future. */
595     { "H"   , OCSD_MEM_SPACE_EL2 }, /* hypervisor - EL2 NS */
596     { "P"   , OCSD_MEM_SPACE_EL1N }, /* privileged - EL1 NS */
597     { "NP"   , OCSD_MEM_SPACE_EL1N }, /* non secure privileged - EL1 NS */
598     { "SP"   , OCSD_MEM_SPACE_EL1S }, /* secure privileged - EL1 S */
599     /* table terminator */
600     { "", OCSD_MEM_SPACE_NONE},
601 };
602 
603 /* get mem space from input string */
getMemSpaceFromString(const std::string & memspace)604 ocsd_mem_space_acc_t CreateDcdTreeFromSnapShot::getMemSpaceFromString(const std::string& memspace)
605 {
606 
607 
608     ocsd_mem_space_acc_t mem_space = OCSD_MEM_SPACE_ANY;
609     if (memspace.length() > 0) {
610         int i = 0;
611 
612         while (space_map[i].memspace != OCSD_MEM_SPACE_NONE) {
613             if (space_map[i].key_name == memspace) {
614                 mem_space = space_map[i].memspace;
615                 break;
616             }
617             i++;
618         }
619     }
620     return mem_space;
621 }
622 
processDumpfiles(std::vector<Parser::DumpDef> & dumps)623 ocsd_err_t CreateDcdTreeFromSnapShot::processDumpfiles(std::vector<Parser::DumpDef> &dumps)
624 {
625     std::string dumpFilePathName;
626     std::vector<Parser::DumpDef>::const_iterator it;
627     ocsd_mem_space_acc_t mem_space;
628     ocsd_err_t err = OCSD_OK;
629 
630     it = dumps.begin();
631     while(it != dumps.end())
632     {
633         dumpFilePathName = m_pReader->getSnapShotDir() + it->path;
634         ocsd_file_mem_region_t region;
635         ocsd_err_t err = OCSD_OK;
636 
637         region.start_address = it->address;
638         region.file_offset = it->offset;
639         region.region_size = it->length;
640         mem_space = getMemSpaceFromString(it->space);
641 
642         // ensure we respect optional length and offset parameter and
643         // allow multiple dump entries with same file name to define regions
644         if (!TrcMemAccessorFile::isExistingFileAccessor(dumpFilePathName))
645             err = m_pDecodeTree->addBinFileRegionMemAcc(&region, 1, mem_space, dumpFilePathName);
646         else
647             err = m_pDecodeTree->updateBinFileRegionMemAcc(&region, 1, mem_space, dumpFilePathName);
648         if(err != OCSD_OK)
649         {
650             std::ostringstream oss;
651             oss << "Failed to create memory accessor for file " << dumpFilePathName << ".";
652             LogError(ocsdError(OCSD_ERR_SEV_ERROR,err,oss.str()));
653         }
654         it++;
655     }
656     return err;
657 }
658 
659 /* End of File ss_to_dcdtree.cpp */
660