XmlAnalyzer.h 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449
  1. //
  2. // Copyright (c) 2008-2020 the Urho3D project.
  3. //
  4. // Permission is hereby granted, free of charge, to any person obtaining a copy
  5. // of this software and associated documentation files (the "Software"), to deal
  6. // in the Software without restriction, including without limitation the rights
  7. // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  8. // copies of the Software, and to permit persons to whom the Software is
  9. // furnished to do so, subject to the following conditions:
  10. //
  11. // The above copyright notice and this permission notice shall be included in
  12. // all copies or substantial portions of the Software.
  13. //
  14. // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  15. // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  16. // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  17. // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  18. // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  19. // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  20. // THE SOFTWARE.
  21. //
  22. #pragma once
  23. #include <PugiXml/pugixml.hpp>
  24. #include <string>
  25. #include <memory>
  26. #include <vector>
  27. #include <map>
  28. #include "XmlSourceData.h"
  29. #include "Utils.h"
  30. using namespace pugi;
  31. using namespace std;
  32. // <type>...</type>
  33. class TypeAnalyzer
  34. {
  35. private:
  36. string fullType_;
  37. string name_;
  38. bool isConst_;
  39. bool isPointer_; // *
  40. bool isReference_; // &
  41. bool isRvalueReference_; // &&
  42. bool isDoublePointer_; // **
  43. bool isRefToPoiner_; // *&
  44. string templateParams_;
  45. public:
  46. TypeAnalyzer(xml_node type, const map<string, string>& templateSpecialization = map<string, string>());
  47. string ToString() const { return fullType_; }
  48. string GetName() const { return name_; }
  49. bool IsConst() const { return isConst_; }
  50. bool IsPointer() const { return isPointer_; }
  51. bool IsReference() const { return isReference_; }
  52. bool IsRvalueReference() const { return isRvalueReference_; }
  53. bool IsDoublePointer() const { return isDoublePointer_; }
  54. bool IsRefToPointer() const { return isRefToPoiner_; }
  55. bool IsTemplate() const { return templateParams_.length() > 0; }
  56. string GetTemplateParams() { return templateParams_; }
  57. string GetNameWithTemplateParams() const { return IsTemplate() ? name_ + "<" + templateParams_ + ">" : name_; }
  58. };
  59. // <memberdef kind="function">
  60. // <param>...</param>
  61. class ParamAnalyzer
  62. {
  63. private:
  64. xml_node node_;
  65. map<string, string> templateSpecialization_;
  66. public:
  67. ParamAnalyzer(xml_node param, const map<string, string>& templateSpecialization = map<string, string>());
  68. xml_node GetNode() const { return node_; }
  69. string ToString() const; // "type name"
  70. // <param>
  71. // <type>....</type>
  72. TypeAnalyzer GetType() const;
  73. // <param>
  74. // <declname>....</declname>
  75. string GetDeclname() const;
  76. // <param>
  77. // <defval>....</defval>
  78. string GetDefval() const; // Default value
  79. };
  80. // <memberdef>
  81. inline bool IsMemberdef(xml_node node) { return node.name() == string("memberdef"); }
  82. // <compounddef>
  83. inline bool IsCompounddef(xml_node node) { return node.name() == string("compounddef"); }
  84. // <member>
  85. inline bool IsMember(xml_node node) { return node.name() == string("member"); }
  86. // <sectiondef>
  87. inline bool IsSectiondef(xml_node node) { return node.name() == string("sectiondef"); }
  88. // <enumvalue>
  89. inline bool IsEnumvalue(xml_node node) { return node.name() == string("enumvalue"); }
  90. // <compounddef>
  91. // <compoundname>...</compoundname>
  92. string ExtractCompoundname(xml_node compounddef);
  93. // <compounddef>
  94. // <sectiondef kind="xxx">...</sectiondef>
  95. xml_node FindSectiondef(xml_node compounddef, const string& kind);
  96. // <memberdef static="yes">
  97. bool IsStatic(xml_node memberdef);
  98. // <memberdef kind="function" explicit="yes">
  99. bool IsExplicit(xml_node memberdef);
  100. // <memberdef>
  101. // <definition>...</definition>
  102. string ExtractDefinition(xml_node memberdef);
  103. // <memberdef>
  104. // <argsstring>...</argsstring>
  105. string ExtractArgsstring(xml_node memberdef);
  106. // <memberdef kind="function">
  107. // <templateparamlist>
  108. // <param>...</param>
  109. // <param>...</param>
  110. vector<string> ExtractTemplateParams(xml_node memberdef);
  111. // <memberdef prot="...">
  112. string ExtractProt(xml_node memberdef);
  113. // <memberdef>
  114. // <type>...</type>
  115. TypeAnalyzer ExtractType(xml_node memberdef, const map<string, string>& templateSpecialization = map<string, string>());
  116. // <memberdef kind="function">
  117. // <param>...</param>
  118. // <param>...</param>
  119. vector<ParamAnalyzer> ExtractParams(xml_node memberdef, const map<string, string>& templateSpecialization = map<string, string>());
  120. // <memberdef kind="function">
  121. // <param>...</param>
  122. // <param>...</param>
  123. string JoinParamsTypes(xml_node memberdef, const map<string, string>& templateSpecialization = map<string, string>());
  124. string JoinParamsNames(xml_node memberdef, bool skipContext = false);
  125. // <compounddef|memberdef id="...">
  126. string ExtractID(xml_node node);
  127. // <compounddef|memberdef|member|sectiondef kind="...">
  128. string ExtractKind(xml_node node);
  129. // <memberdef|enumvalue>
  130. // <name>...</name>
  131. string ExtractName(xml_node node);
  132. // <compounddef|memberdef>
  133. // <location line="...">
  134. string ExtractLine(xml_node node);
  135. // <compounddef|memberdef>
  136. // <location column="...">
  137. string ExtractColumn(xml_node node);
  138. // <compounddef|memberdef>
  139. // <briefdescription>...</briefdescription>
  140. // <detaileddescription>...</detaileddescription>
  141. string ExtractComment(xml_node node);
  142. // <compounddef|memberdef>
  143. // <location ...>
  144. // Extract header file path and convert to relative.
  145. // Return empty string when declared in *.cpp
  146. string ExtractHeaderFile(xml_node node);
  147. // <compounddef|memberdef>
  148. // <templateparamlist>
  149. bool IsTemplate(xml_node node);
  150. // ============================================================================
  151. // <compounddef kind="namespace">
  152. // <sectiondef kind="enum">
  153. // <memberdef kind="enum">...</memberdef>
  154. class EnumAnalyzer
  155. {
  156. xml_node memberdef_;
  157. public:
  158. EnumAnalyzer(xml_node memberdef);
  159. string GetTypeName() const { return ExtractName(memberdef_); }
  160. string GetHeaderFile() const { return ExtractHeaderFile(memberdef_); }
  161. string GetComment() const { return ExtractComment(memberdef_); }
  162. bool IsInternal() const { return GetHeaderFile().empty(); } // true if declared in .cpp file
  163. string GetBaseType() const;
  164. string GetLocation() const;
  165. // <memberdef kind="enum">
  166. // <enumvalue><name>...</name></enumvalue>
  167. // <enumvalue><name>...</name></enumvalue>
  168. vector<string> GetEnumerators() const;
  169. };
  170. // ============================================================================
  171. // <compounddef kind="namespace">
  172. // <sectiondef kind="var">
  173. // <memberdef kind="variable">...</memberdef>
  174. class GlobalVariableAnalyzer
  175. {
  176. xml_node memberdef_;
  177. public:
  178. GlobalVariableAnalyzer(xml_node memberdef);
  179. string GetName() const { return ExtractName(memberdef_); }
  180. string GetHeaderFile() const { return ExtractHeaderFile(memberdef_); }
  181. bool IsStatic() const { return ::IsStatic(memberdef_); }
  182. TypeAnalyzer GetType() const { return ExtractType(memberdef_); }
  183. bool IsArray() const { return StartsWith(ExtractArgsstring(memberdef_), "["); }
  184. string GetLocation() const;
  185. };
  186. // ============================================================================
  187. class ClassFunctionAnalyzer;
  188. class ClassVariableAnalyzer;
  189. // <compounddef kind="class|struct">...</compounddef>
  190. class ClassAnalyzer
  191. {
  192. private:
  193. xml_node compounddef_;
  194. vector<xml_node> GetMemberdefs() const;
  195. public:
  196. ClassAnalyzer(xml_node compounddef);
  197. string GetClassName() const;
  198. string GetComment() const { return ExtractComment(compounddef_); }
  199. string GetHeaderFile() const { return ExtractHeaderFile(compounddef_); }
  200. string GetKind() const { return ExtractKind(compounddef_); }
  201. bool IsInternal() const;
  202. bool IsTemplate() const { return ::IsTemplate(compounddef_); }
  203. vector<ClassFunctionAnalyzer> GetFunctions() const;
  204. vector<ClassVariableAnalyzer> GetVariables() const;
  205. bool ContainsFunction(const string& name) const;
  206. ClassFunctionAnalyzer GetFunction(const string& name) const;
  207. int NumFunctions(const string& name) const;
  208. bool IsRefCounted() const { return ContainsFunction("AddRef") && ContainsFunction("ReleaseRef"); }
  209. bool HasDestructor() const { return ContainsFunction("~" + GetClassName()); }
  210. bool HasThisConstructor() const;
  211. bool IsAbstract() const;
  212. string GetLocation() const { return GetKind() + " " + GetClassName() + " | File: " + GetHeaderFile(); }
  213. bool AllFloats() const;
  214. bool AllInts() const;
  215. bool IsPod() const;
  216. shared_ptr<ClassAnalyzer> GetBaseClass() const;
  217. vector<ClassAnalyzer> GetBaseClasses() const;
  218. vector<ClassAnalyzer> GetAllBaseClasses() const;
  219. };
  220. // ============================================================================
  221. // <compounddef kind="class|struct">
  222. // <sectiondef>
  223. // <memberdef kind="function">...</memberdef>
  224. class ClassFunctionAnalyzer
  225. {
  226. ClassAnalyzer classAnalyzer_;
  227. xml_node memberdef_;
  228. public:
  229. ClassFunctionAnalyzer(ClassAnalyzer classAnalyzer, xml_node memberdef);
  230. ClassAnalyzer GetClass() const { return classAnalyzer_; }
  231. xml_node GetMemberdef() const { return memberdef_; }
  232. // <memberdef kind="function" virt="...">
  233. string GetVirt() const;
  234. bool IsPureVirtual() const { return GetVirt() == "pure-virtual"; }
  235. // <memberdef kind="function" const="yes">
  236. bool IsConst() const;
  237. // <memberdef>
  238. // <reimplements refid="..."></reimplements>
  239. shared_ptr<ClassFunctionAnalyzer> Reimplements() const;
  240. string GetName() const { return ExtractName(memberdef_); }
  241. string GetClassName() const { return classAnalyzer_.GetClassName(); }
  242. string GetContainsClassName() const; // May this function defined in parent class, so return name o class, real define this function
  243. string GetLine() const { return ExtractLine(memberdef_); }
  244. string GetColumn() const { return ExtractColumn(memberdef_); }
  245. string GetComment() const { return ExtractComment(memberdef_); }
  246. bool IsStatic() const { return ::IsStatic(memberdef_); }
  247. bool IsPublic() const { return ExtractProt(memberdef_) == "public"; }
  248. bool IsThisConstructor() const { return GetName() == GetClassName(); }
  249. bool IsParentConstructor() const;
  250. bool IsThisDestructor() const { return GetName() == "~" + GetClassName(); }
  251. bool IsParentDestructor() const;
  252. string GetLocation() const;
  253. string GetHeaderFile() const { return ExtractHeaderFile(memberdef_); }
  254. TypeAnalyzer GetReturnType(const map<string, string>& templateSpecialization = map<string, string>()) const { return ExtractType(memberdef_, templateSpecialization); }
  255. bool CanBeGetProperty() const;
  256. bool CanBeSetProperty() const;
  257. bool IsTemplate() const { return ::IsTemplate(memberdef_); }
  258. bool IsExplicit() const { return ::IsExplicit(memberdef_); }
  259. bool IsDefine() const { return CONTAINS(SourceData::defines_, GetName()); }
  260. bool IsDeleted() const { return EndsWith(ExtractArgsstring(memberdef_), "=delete"); }
  261. bool IsConsversionOperator() const { return StartsWith(GetName(), "operator "); }
  262. vector<ParamAnalyzer> GetParams() const { return ExtractParams(memberdef_); }
  263. string JoinParamsNames(bool skipContext = false) const { return ::JoinParamsNames(memberdef_, skipContext); }
  264. string JoinParamsTypes() const { return ::JoinParamsTypes(memberdef_); }
  265. };
  266. // ============================================================================
  267. // <compounddef kind="class|struct">
  268. // <sectiondef>
  269. // <memberdef kind="variable">...</memberdef>
  270. class ClassVariableAnalyzer
  271. {
  272. ClassAnalyzer classAnalyzer_;
  273. xml_node memberdef_;
  274. public:
  275. ClassVariableAnalyzer(ClassAnalyzer classAnalyzer, xml_node memberdef);
  276. bool IsStatic() const { return ::IsStatic(memberdef_); }
  277. TypeAnalyzer GetType() const { return ExtractType(memberdef_); }
  278. string GetName() const { return ExtractName(memberdef_); }
  279. string GetComment() const { return ExtractComment(memberdef_); }
  280. bool IsPublic() const { return ExtractProt(memberdef_) == "public"; }
  281. string GetHeaderFile() const { return ExtractHeaderFile(memberdef_); }
  282. string GetLocation() const;
  283. string GetClassName() const { return classAnalyzer_.GetClassName(); }
  284. bool IsArray() const { return StartsWith(ExtractArgsstring(memberdef_), "["); };
  285. };
  286. // ============================================================================
  287. // <compounddef kind="namespace">
  288. // <sectiondef kind="func">
  289. // <memberdef kind="function">...</memberdef>
  290. class GlobalFunctionAnalyzer
  291. {
  292. xml_node memberdef_;
  293. public:
  294. GlobalFunctionAnalyzer(xml_node memberdef);
  295. string GetName() const { return ExtractName(memberdef_); }
  296. string GetHeaderFile() const { return ExtractHeaderFile(memberdef_); }
  297. bool IsTemplate() const { return ::IsTemplate(memberdef_); }
  298. string GetComment() const { return ExtractComment(memberdef_); }
  299. vector<ParamAnalyzer> GetParams(const map<string, string>& templateSpecialization = map<string, string>()) const { return ExtractParams(memberdef_, templateSpecialization); }
  300. TypeAnalyzer GetReturnType(const map<string, string>& templateSpecialization = map<string, string>()) const { return ExtractType(memberdef_, templateSpecialization); }
  301. xml_node GetMemberdef() const { return memberdef_; }
  302. vector<string> GetTemplateParams() const { return ExtractTemplateParams(memberdef_); }
  303. string JoinParamsNames() const { return ::JoinParamsNames(memberdef_); }
  304. string JoinParamsTypes() const { return ::JoinParamsTypes(memberdef_); }
  305. bool IsDefine() const { return CONTAINS(SourceData::defines_, GetName()); }
  306. string GetLocation() const;
  307. };
  308. // ============================================================================
  309. // <compounddef kind="class|struct">
  310. // <sectiondef kind="public-static-func">
  311. // <memberdef kind="function" prot="public" static="yes">...</memberdef>
  312. class ClassStaticFunctionAnalyzer
  313. {
  314. ClassAnalyzer classAnalyzer_;
  315. xml_node memberdef_;
  316. public:
  317. ClassStaticFunctionAnalyzer(ClassAnalyzer classAnalyzer, xml_node memberdef);
  318. string GetName() const { return ExtractName(memberdef_); }
  319. string GetHeaderFile() const { return ExtractHeaderFile(memberdef_); }
  320. bool IsTemplate() const { return ::IsTemplate(memberdef_); }
  321. string GetComment() const { return ExtractComment(memberdef_); }
  322. vector<ParamAnalyzer> GetParams(const map<string, string>& templateSpecialization = map<string, string>()) const { return ExtractParams(memberdef_, templateSpecialization); }
  323. TypeAnalyzer GetReturnType(const map<string, string>& templateSpecialization = map<string, string>()) const { return ExtractType(memberdef_, templateSpecialization); }
  324. xml_node GetMemberdef() const { return memberdef_; }
  325. vector<string> GetTemplateParams() const { return ExtractTemplateParams(memberdef_); }
  326. string GetClassName() const { return classAnalyzer_.GetClassName(); }
  327. bool IsDefine() const { return CONTAINS(SourceData::defines_, GetName()); };
  328. string JoinParamsNames() const { return ::JoinParamsNames(memberdef_); }
  329. string JoinParamsTypes() const { return ::JoinParamsTypes(memberdef_); };
  330. string GetLocation() const;
  331. };
  332. // ============================================================================
  333. // <memberdef kind="typedef">
  334. // <definition>using ...</definition>
  335. class UsingAnalyzer
  336. {
  337. private:
  338. xml_node memberdef_;
  339. public:
  340. UsingAnalyzer(xml_node memberdef);
  341. string GetIdentifier() const;
  342. };
  343. // ============================================================================
  344. // <compounddef kind = "namespace">...</compounddef>
  345. class NamespaceAnalyzer
  346. {
  347. private:
  348. xml_node compounddef_;
  349. public:
  350. NamespaceAnalyzer(xml_node compounddef);
  351. // <compounddef kind="namespace">
  352. // <sectiondef kind="enum">
  353. // <memberdef kind="enum">...</memberdef>
  354. // <memberdef kind="enum">...</memberdef>
  355. vector<EnumAnalyzer> GetEnums();
  356. // <compounddef kind="namespace">
  357. // <sectiondef kind="var">
  358. // <memberdef kind="variable">...</memberdef>
  359. // <memberdef kind="variable">...</memberdef>
  360. vector<GlobalVariableAnalyzer> GetVariables();
  361. // <compounddef kind="namespace">
  362. // <sectiondef kind="func">
  363. // <memberdef kind="function">...</memberdef>
  364. // <memberdef kind="function">...</memberdef>
  365. vector<GlobalFunctionAnalyzer> GetFunctions();
  366. };