3 * @author Nicolas VIVIEN
6 * @note CopyRight Nicolas VIVIEN
8 * @brief COD debug file parser
9 * RIM's JDE generates several files when you build a COD application.
10 * Indeed, with the COD files for the device, we have a ".debug" file.
11 * This file is usefull to debug an application from JVM.
12 * This tool is a parser to understand these ".debug" files.
15 * - 2009/08/01 : N. VIVIEN
19 * Copyright (C) 2009-2010, Nicolas VIVIEN
21 * This program is free software; you can redistribute it and/or modify
22 * it under the terms of the GNU General Public License as published by
23 * the Free Software Foundation; either version 2 of the License, or
24 * (at your option) any later version.
26 * This program is distributed in the hope that it will be useful,
27 * but WITHOUT ANY WARRANTY; without even the implied warranty of
28 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
30 * See the GNU General Public License in the COPYING file at the
31 * root directory of this project for more details.
40 #include <sys/types.h>
44 #include "dp_parser.h"
45 #include "dp_codinfo.h"
59 #define DEBUG_FILE_EXT ".debug"
62 void searchDebugFile(JDGDebugFileList
&list
)
69 while( (entry
= readdir(path
)) ) {
72 if (strlen(entry
->d_name
) < strlen(DEBUG_FILE_EXT
))
75 offset
= strlen(entry
->d_name
) - strlen(DEBUG_FILE_EXT
);
77 if (!strcmp(entry
->d_name
+ offset
, DEBUG_FILE_EXT
)) {
78 ifstream
file(entry
->d_name
);
82 // Parse header section
83 info
.parseHeaderSection(file
);
85 // Add element to list
86 list
.AddElement(info
.getUniqueId(), info
.getAppName(), entry
->d_name
);
94 bool loadDebugInfo(JDGDebugFileList
&list
, const char *filename
, JDGCodInfo
&info
)
99 vector
<JDGDebugFileEntry
>::iterator b
= list
.begin();
101 for( ; b
!= list
.end(); b
++ ) {
102 JDGDebugFileEntry entry
= (*b
);
104 if (entry
.fileName
== string(filename
)) {
105 info
.loadDebugFile(filename
);
114 bool loadDebugInfo(JDGDebugFileList
&list
, const uint32_t uniqueId
, const std::string module
, JDGCodInfo
&info
)
116 vector
<JDGDebugFileEntry
>::iterator b
= list
.begin();
118 for( ; b
!= list
.end(); b
++ ) {
119 JDGDebugFileEntry entry
= (*b
);
121 if ((entry
.uniqueId
== uniqueId
) && (entry
.appName
== module
)) {
122 info
.loadDebugFile(entry
.fileName
.c_str());
131 // JDGDebugFileList class
132 //------------------------
134 void JDGDebugFileList::AddElement(uint32_t uniqueid
, std::string appname
, std::string filename
)
136 JDGDebugFileEntry entry
;
138 entry
.uniqueId
= uniqueid
;
139 entry
.appName
= appname
;
140 entry
.fileName
= filename
;
146 void JDGDebugFileList::Dump(std::ostream
&os
) const
148 const_iterator i
= begin(), e
= end();
150 os
<< " UniqueID " << "|";
151 os
<< " Module Name " << "|";
152 os
<< " File Name " << endl
;
154 os
<< "------------+";
155 os
<< "--------------------------+";
156 os
<< "--------------------------";
159 for( ; i
!= e
; ++i
) {
165 void JDGDebugFileEntry::Dump(std::ostream
&os
) const
167 os
<< " 0x" << setfill('0') << setw(8) << hex
<< uniqueId
<< " |";
168 os
<< " " << appName
<< setfill(' ') << setw(24) << " |";
169 os
<< " " << fileName
<< endl
;
173 // JDGClassList class
174 //---------------------------
177 void JDGClassList::createDefaultEntries() {
181 entry
.classPath
= "com.rim.resources";
182 entry
.className
= "net_rim_rimsecuridlibRIMResources";
186 entry
.classPath
= "net.rim.device.cldc.impl.softtoken.rimsecuridlib";
187 entry
.className
= "RimSecurIDLib";
191 entry
.classPath
= "net.rim.device.cldc.impl.softtoken.rimsecuridlib";
192 entry
.className
= "RimDatabaseFullException";
196 entry
.classPath
= "net.rim.device.cldc.impl.softtoken.rimsecuridlib";
197 entry
.className
= "RimDecryptFailException";
201 entry
.classPath
= "net.rim.device.cldc.impl.softtoken.rimsecuridlib";
202 entry
.className
= "RimDuplicateNameException";
206 entry
.classPath
= "net.rim.device.cldc.impl.softtoken.rimsecuridlib";
207 entry
.className
= "RimDuplicateTokenException";
211 entry
.classPath
= "net.rim.device.cldc.impl.softtoken.rimsecuridlib";
212 entry
.className
= "RimInvalidParamException";
216 entry
.classPath
= "net.rim.device.cldc.impl.softtoken.rimsecuridlib";
217 entry
.className
= "RimSecurIDLib";
221 entry
.classPath
= "net.rim.device.cldc.impl.softtoken.rimsecuridlib";
222 entry
.className
= "RimWrongDeviceIDException";
226 entry
.classPath
= "net.rim.device.cldc.impl.softtoken.rimsecuridlib";
227 entry
.className
= "RimWrongFormFactorException";
233 //------------------------
235 bool JDGCodInfo::loadDebugFile(const char *filename
)
237 if (filename
== NULL
)
240 ifstream
file(filename
);
243 parseHeaderSection(file
);
245 // Parse type area zone
246 parseTypeSection(file
);
252 uint32_t JDGCodInfo::getUniqueId()
258 string
JDGCodInfo::getAppName()
264 // Private API - Section parsing
265 //-------------------------------
267 void JDGCodInfo::parseHeaderSection(ifstream
&input
)
271 type
= parseNextHeaderField(input
);
273 if (type
!= COD_DEBUG_UNIQUEID_HEADERFIELD
)
276 type
= parseNextHeaderField(input
);
278 if (type
!= COD_DEBUG_APPNAME_HEADERFIELD
)
283 void JDGCodInfo::parseTypeSection(ifstream
&input
)
289 // Read number of declared type content into this section
290 nbr
= ParseInteger(input
);
295 while (!input
.eof()) {
296 type
= parseNextTypeField(input
);
298 if (type
== COD_DEBUG_NONE_FIELD
)
304 // Read again number of declared type content into this section
305 // We have to find the same value
306 check
= ParseInteger(input
);
309 cout
<< "Nbr = " << dec
<< nbr
<< " / Count = " << dec
<< count
<< " / check = " << check
<< endl
;
313 uint32_t JDGCodInfo::parseNextHeaderField(ifstream
&input
)
315 uint32_t type
= ParseInteger(input
);
318 case COD_DEBUG_UNIQUEID_HEADERFIELD
:
319 parseUniqueId(input
);
322 case COD_DEBUG_APPNAME_HEADERFIELD
:
334 uint32_t JDGCodInfo::parseNextTypeField(ifstream
&input
)
336 uint32_t type
= ParseInteger(input
);
339 case COD_DEBUG_NONE_FIELD
:
342 case COD_DEBUG_BOOLEAN_FIELD
:
346 case COD_DEBUG_BYTE_FIELD
:
350 case COD_DEBUG_CHAR_FIELD
:
354 case COD_DEBUG_SHORT_FIELD
:
358 case COD_DEBUG_INT_FIELD
:
362 case COD_DEBUG_LONG_FIELD
:
366 case COD_DEBUG_CLASS_FIELD
:
370 case COD_DEBUG_ARRAY_FIELD
:
374 case COD_DEBUG_VOID_FIELD
:
378 case COD_DEBUG_DOUBLE_FIELD
:
383 cout
<< "Type unknown ! " << hex
<< type
<< endl
;
391 void JDGCodInfo::parseUniqueId(ifstream
&input
)
393 uniqueId
= ParseInteger(input
);
397 void JDGCodInfo::parseAppName(ifstream
&input
)
399 uint32_t len
= ParseInteger(input
);
401 appName
= ParseString(input
, len
);
405 void JDGCodInfo::parseBoolean(ifstream
&input
)
407 uint32_t len
= ParseInteger(input
);
409 string str
= ParseString(input
, len
);
411 cout
<< "JDGCodInfo::parseBoolean" << endl
;
412 cout
<< " name : " << str
<< endl
;
416 void JDGCodInfo::parseByte(ifstream
&input
)
418 uint32_t len
= ParseInteger(input
);
420 string str
= ParseString(input
, len
);
422 cout
<< "JDGCodInfo::parseByte" << endl
;
423 cout
<< " name : " << str
<< endl
;
427 void JDGCodInfo::parseChar(ifstream
&input
)
429 uint32_t len
= ParseInteger(input
);
431 string str
= ParseString(input
, len
);
433 cout
<< "JDGCodInfo::parseChar" << endl
;
434 cout
<< " name : " << str
<< endl
;
438 void JDGCodInfo::parseShort(ifstream
&input
)
440 uint32_t len
= ParseInteger(input
);
442 string str
= ParseString(input
, len
);
444 cout
<< "JDGCodInfo::parseShort" << endl
;
445 cout
<< " name : " << str
<< endl
;
449 void JDGCodInfo::parseInt(ifstream
&input
)
451 uint32_t len
= ParseInteger(input
);
453 string str
= ParseString(input
, len
);
455 cout
<< "JDGCodInfo::parseInt" << endl
;
456 cout
<< " name : " << str
<< endl
;
460 void JDGCodInfo::parseLong(ifstream
&input
)
462 uint32_t len
= ParseInteger(input
);
464 string str
= ParseString(input
, len
);
466 cout
<< "JDGCodInfo::parseLong" << endl
;
467 cout
<< " name : " << str
<< endl
;
471 void JDGCodInfo::parseClass(ifstream
&input
)
475 JDGClassEntry object
;
477 cout
<< "JDGCodInfo::parseClass" << endl
;
479 len
= ParseInteger(input
);
481 object
.className
= ParseString(input
, len
);
483 object
.type
= ParseInteger(input
);
484 object
.unknown02
= ParseInteger(input
);
485 object
.unknown03
= ParseInteger(input
);
486 object
.id
= ParseInteger(input
);
488 len
= ParseInteger(input
);
491 object
.classPath
= "com.barry." + appName
;
492 else if (len
!= 0xFFFFFF)
493 object
.classPath
= ParseString(input
, len
);
495 len
= ParseInteger(input
);
497 object
.sourceFile
= ParseString(input
, len
);
499 object
.unknown05
= ParseInteger(input
);
500 object
.unknown06
= ParseInteger(input
);
501 object
.unknown07
= ParseInteger(input
);
502 object
.unknown08
= ParseInteger(input
);
504 classList
.push_back(object
);
506 cout
<< " name : " << object
.className
<< endl
;
507 cout
<< " path : " << object
.classPath
<< endl
;
508 cout
<< " type : " << hex
<< object
.type
<< endl
;
509 cout
<< " unknown02 : " << hex
<< object
.unknown02
<< endl
;
510 cout
<< " unknown03 : " << hex
<< object
.unknown03
<< endl
;
511 cout
<< " id : " << hex
<< object
.id
<< endl
;
512 cout
<< " source file : " << object
.sourceFile
<< endl
;
513 cout
<< " unknown05 : " << hex
<< object
.unknown05
<< endl
;
514 cout
<< " unknown06 : " << hex
<< object
.unknown06
<< endl
;
515 cout
<< " unknown07 : " << hex
<< object
.unknown07
<< endl
;
516 cout
<< " unknown08 : " << hex
<< object
.unknown08
<< endl
;
520 void JDGCodInfo::parseArray(ifstream
&input
)
522 uint32_t len
= ParseInteger(input
);
524 string str
= ParseString(input
, len
);
526 cout
<< "JDGCodInfo::parseArray" << endl
;
527 cout
<< " name : " << str
<< endl
;
531 void JDGCodInfo::parseVoid(ifstream
&input
)
533 uint32_t len
= ParseInteger(input
);
535 string str
= ParseString(input
, len
);
537 cout
<< "JDGCodInfo::parseVoid" << endl
;
538 cout
<< " name : " << str
<< endl
;
542 void JDGCodInfo::parseDouble(ifstream
&input
)
544 uint32_t len
= ParseInteger(input
);
546 string str
= ParseString(input
, len
);
548 cout
<< "JDGCodInfo::parseDouble" << endl
;
549 cout
<< " name : " << str
<< endl
;
553 void JDGCodInfo::parseType2(ifstream &input) {
555 uint32_t len = ParseInteger(input);
557 string str = ParseString(input, len);
559 cout << "Type2 : " << str << endl;
561 value = ParseInteger(input);
562 value = ParseInteger(input);
563 value = ParseInteger(input);
564 value = ParseInteger(input);
565 value = ParseInteger(input);
566 value = ParseInteger(input);