cppTypedefType.cxx 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401
  1. // Filename: cppTypedefType.cxx
  2. // Created by: rdb (01Aug14)
  3. //
  4. ////////////////////////////////////////////////////////////////////
  5. //
  6. // PANDA 3D SOFTWARE
  7. // Copyright (c) Carnegie Mellon University. All rights reserved.
  8. //
  9. // All use of this software is subject to the terms of the revised BSD
  10. // license. You should have received a copy of this license along
  11. // with this source code in a file named "LICENSE."
  12. //
  13. ////////////////////////////////////////////////////////////////////
  14. #include "cppTypedefType.h"
  15. #include "cppIdentifier.h"
  16. #include "cppInstanceIdentifier.h"
  17. ////////////////////////////////////////////////////////////////////
  18. // Function: CPPTypedefType::Constructor
  19. // Access: Public
  20. // Description:
  21. ////////////////////////////////////////////////////////////////////
  22. CPPTypedefType::
  23. CPPTypedefType(CPPType *type, const string &name, CPPScope *current_scope) :
  24. CPPType(CPPFile()),
  25. _type(type),
  26. _ident(new CPPIdentifier(name))
  27. {
  28. if (_ident != NULL) {
  29. _ident->_native_scope = current_scope;
  30. }
  31. _subst_decl_recursive_protect = false;
  32. //assert(_type != NULL);
  33. //if (global) {
  34. // _type->_typedefs.push_back(this);
  35. // CPPType::record_alt_name_for(_type, inst->get_local_name());
  36. //}
  37. }
  38. ////////////////////////////////////////////////////////////////////
  39. // Function: CPPTypedefType::Constructor
  40. // Access: Public
  41. // Description:
  42. ////////////////////////////////////////////////////////////////////
  43. CPPTypedefType::
  44. CPPTypedefType(CPPType *type, CPPIdentifier *ident, CPPScope *current_scope) :
  45. CPPType(CPPFile()),
  46. _type(type),
  47. _ident(ident)
  48. {
  49. if (_ident != NULL) {
  50. _ident->_native_scope = current_scope;
  51. }
  52. _subst_decl_recursive_protect = false;
  53. }
  54. ////////////////////////////////////////////////////////////////////
  55. // Function: CPPTypedefType::Constructor
  56. // Access: Public
  57. // Description: Constructs a new CPPTypedefType object that defines a
  58. // typedef to the indicated type according to the type
  59. // and the InstanceIdentifier. The InstanceIdentifier
  60. // pointer is deallocated.
  61. ////////////////////////////////////////////////////////////////////
  62. CPPTypedefType::
  63. CPPTypedefType(CPPType *type, CPPInstanceIdentifier *ii,
  64. CPPScope *current_scope, const CPPFile &file) :
  65. CPPType(file)
  66. {
  67. _type = ii->unroll_type(type);
  68. _ident = ii->_ident;
  69. ii->_ident = NULL;
  70. delete ii;
  71. if (_ident != NULL) {
  72. _ident->_native_scope = current_scope;
  73. }
  74. _subst_decl_recursive_protect = false;
  75. }
  76. ////////////////////////////////////////////////////////////////////
  77. // Function: CPPTypedefType::is_scoped
  78. // Access: Public
  79. // Description:
  80. ////////////////////////////////////////////////////////////////////
  81. bool CPPTypedefType::
  82. is_scoped() const {
  83. if (_ident == NULL) {
  84. return false;
  85. } else {
  86. return _ident->is_scoped();
  87. }
  88. }
  89. ////////////////////////////////////////////////////////////////////
  90. // Function: CPPTypedefType::get_scope
  91. // Access: Public
  92. // Description:
  93. ////////////////////////////////////////////////////////////////////
  94. CPPScope *CPPTypedefType::
  95. get_scope(CPPScope *current_scope, CPPScope *global_scope,
  96. CPPPreprocessor *error_sink) const {
  97. if (_ident == NULL) {
  98. return current_scope;
  99. } else {
  100. return _ident->get_scope(current_scope, global_scope, error_sink);
  101. }
  102. }
  103. ////////////////////////////////////////////////////////////////////
  104. // Function: CPPTypedefType::get_simple_name
  105. // Access: Public, Virtual
  106. // Description:
  107. ////////////////////////////////////////////////////////////////////
  108. string CPPTypedefType::
  109. get_simple_name() const {
  110. if (_ident == NULL) {
  111. return "";
  112. }
  113. return _ident->get_simple_name();
  114. }
  115. ////////////////////////////////////////////////////////////////////
  116. // Function: CPPTypedefType::get_local_name
  117. // Access: Public, Virtual
  118. // Description:
  119. ////////////////////////////////////////////////////////////////////
  120. string CPPTypedefType::
  121. get_local_name(CPPScope *scope) const {
  122. if (_ident == NULL) {
  123. return "";
  124. }
  125. return _ident->get_local_name(scope);
  126. }
  127. ////////////////////////////////////////////////////////////////////
  128. // Function: CPPTypedefType::get_fully_scoped_name
  129. // Access: Public, Virtual
  130. // Description:
  131. ////////////////////////////////////////////////////////////////////
  132. string CPPTypedefType::
  133. get_fully_scoped_name() const {
  134. if (_ident == NULL) {
  135. return "";
  136. }
  137. return _ident->get_fully_scoped_name();
  138. }
  139. ////////////////////////////////////////////////////////////////////
  140. // Function: CPPTypedefType::is_incomplete
  141. // Access: Public, Virtual
  142. // Description: Returns true if the type has not yet been fully
  143. // specified, false if it has.
  144. ////////////////////////////////////////////////////////////////////
  145. bool CPPTypedefType::
  146. is_incomplete() const {
  147. return false;
  148. //return _type->is_incomplete();
  149. }
  150. ////////////////////////////////////////////////////////////////////
  151. // Function: CPPTypedefType::is_tbd
  152. // Access: Public, Virtual
  153. // Description: Returns true if the type, or any nested type within
  154. // the type, is a CPPTBDType and thus isn't fully
  155. // determined right now. In this case, calling
  156. // resolve_type() may or may not resolve the type.
  157. ////////////////////////////////////////////////////////////////////
  158. bool CPPTypedefType::
  159. is_tbd() const {
  160. if (_ident != NULL && _ident->is_tbd()) {
  161. return true;
  162. }
  163. return _type->is_tbd();
  164. }
  165. ////////////////////////////////////////////////////////////////////
  166. // Function: CPPTypedefType::is_fully_specified
  167. // Access: Public, Virtual
  168. // Description: Returns true if this declaration is an actual,
  169. // factual declaration, or false if some part of the
  170. // declaration depends on a template parameter which has
  171. // not yet been instantiated.
  172. ////////////////////////////////////////////////////////////////////
  173. bool CPPTypedefType::
  174. is_fully_specified() const {
  175. if (_ident != NULL && !_ident->is_fully_specified()) {
  176. return false;
  177. }
  178. return CPPDeclaration::is_fully_specified() &&
  179. _type->is_fully_specified();
  180. }
  181. ////////////////////////////////////////////////////////////////////
  182. // Function: CPPTypedefType::substitute_decl
  183. // Access: Public, Virtual
  184. // Description:
  185. ////////////////////////////////////////////////////////////////////
  186. CPPDeclaration *CPPTypedefType::
  187. substitute_decl(CPPDeclaration::SubstDecl &subst,
  188. CPPScope *current_scope, CPPScope *global_scope) {
  189. if (_ident != NULL && _ident->get_scope(current_scope, global_scope) == global_scope) {
  190. // Hack... I know that size_t etc is supposed to work fine, so
  191. // preserve these top-level typedefs.
  192. CPPDeclaration *top =
  193. CPPType::substitute_decl(subst, current_scope, global_scope);
  194. if (top != this) {
  195. return top;
  196. }
  197. top = new CPPTypedefType(*this);
  198. subst.insert(SubstDecl::value_type(this, top));
  199. return top;
  200. }
  201. return _type->substitute_decl(subst, current_scope, global_scope);
  202. // Bah, this doesn't seem to work, and I can't figure out why.
  203. // Well, for now, let's just substitute it with the type we're
  204. // pointing to. This is not a huge deal for now, until we find
  205. // that we need to preserve these typedefs.
  206. /*
  207. CPPDeclaration *top =
  208. CPPType::substitute_decl(subst, current_scope, global_scope);
  209. if (top != this) {
  210. return top;
  211. }
  212. if (_subst_decl_recursive_protect) {
  213. // We're already executing this block; we'll have to return a
  214. // proxy to the type which we'll define later.
  215. CPPTypeProxy *proxy = new CPPTypeProxy;
  216. _proxies.push_back(proxy);
  217. assert(proxy != NULL);
  218. return proxy;
  219. }
  220. _subst_decl_recursive_protect = true;
  221. CPPTypedefType *rep = new CPPTypedefType(*this);
  222. CPPDeclaration *new_type =
  223. _type->substitute_decl(subst, current_scope, global_scope);
  224. rep->_type = new_type->as_type();
  225. if (rep->_type == NULL) {
  226. rep->_type = _type;
  227. }
  228. if (_ident != NULL) {
  229. rep->_ident =
  230. _ident->substitute_decl(subst, current_scope, global_scope);
  231. }
  232. if (rep->_type == _type && rep->_ident == _ident) {
  233. delete rep;
  234. rep = this;
  235. }
  236. rep = CPPType::new_type(rep)->as_typedef_type();
  237. subst.insert(SubstDecl::value_type(this, rep));
  238. _subst_decl_recursive_protect = false;
  239. // Now fill in all the proxies we created for our recursive
  240. // references.
  241. Proxies::iterator pi;
  242. for (pi = _proxies.begin(); pi != _proxies.end(); ++pi) {
  243. (*pi)->_actual_type = rep;
  244. }
  245. return rep; */
  246. }
  247. ////////////////////////////////////////////////////////////////////
  248. // Function: CPPFunctionType::resolve_type
  249. // Access: Public, Virtual
  250. // Description: If this CPPType object is a forward reference or
  251. // other nonspecified reference to a type that might now
  252. // be known a real type, returns the real type.
  253. // Otherwise returns the type itself.
  254. ////////////////////////////////////////////////////////////////////
  255. CPPType *CPPTypedefType::
  256. resolve_type(CPPScope *current_scope, CPPScope *global_scope) {
  257. CPPType *ptype = _type->resolve_type(current_scope, global_scope);
  258. if (ptype != _type) {
  259. CPPTypedefType *rep = new CPPTypedefType(*this);
  260. rep->_type = ptype;
  261. return CPPType::new_type(rep);
  262. }
  263. return this;
  264. }
  265. ////////////////////////////////////////////////////////////////////
  266. // Function: CPPTypedefType::is_equivalent_type
  267. // Access: Public, Virtual
  268. // Description: This is a little more forgiving than is_equal(): it
  269. // returns true if the types appear to be referring to
  270. // the same thing, even if they may have different
  271. // pointers or somewhat different definitions. It's
  272. // useful for parameter matching, etc.
  273. ////////////////////////////////////////////////////////////////////
  274. bool CPPTypedefType::
  275. is_equivalent(const CPPType &other) const {
  276. CPPType *ot = (CPPType *)&other;
  277. // Unwrap all the typedefs to get to where it is pointing.
  278. while (ot->get_subtype() == ST_typedef) {
  279. ot = ot->as_typedef_type()->_type;
  280. }
  281. // Compare the unwrapped type to what we are pointing to.
  282. // If we are pointing to a typedef ourselves, then this will
  283. // automatically recurse.
  284. return _type->is_equivalent(*ot);
  285. }
  286. ////////////////////////////////////////////////////////////////////
  287. // Function: CPPTypedefType::output
  288. // Access: Public, Virtual
  289. // Description:
  290. ////////////////////////////////////////////////////////////////////
  291. void CPPTypedefType::
  292. output(ostream &out, int indent_level, CPPScope *scope, bool complete) const {
  293. string name;
  294. if (_ident != NULL) {
  295. name = _ident->get_local_name(scope);
  296. }
  297. if (complete) {
  298. out << "typedef ";
  299. _type->output_instance(out, indent_level, scope, false, "", name);
  300. } else {
  301. out << name;
  302. }
  303. }
  304. ////////////////////////////////////////////////////////////////////
  305. // Function: CPPTypedefType::get_subtype
  306. // Access: Public, Virtual
  307. // Description:
  308. ////////////////////////////////////////////////////////////////////
  309. CPPDeclaration::SubType CPPTypedefType::
  310. get_subtype() const {
  311. return ST_typedef;
  312. }
  313. ////////////////////////////////////////////////////////////////////
  314. // Function: CPPTypedefType::as_typedef_type
  315. // Access: Public, Virtual
  316. // Description:
  317. ////////////////////////////////////////////////////////////////////
  318. CPPTypedefType *CPPTypedefType::
  319. as_typedef_type() {
  320. return this;
  321. }
  322. ////////////////////////////////////////////////////////////////////
  323. // Function: CPPTypedefType::is_equal
  324. // Access: Protected, Virtual
  325. // Description: Called by CPPDeclaration() to determine whether this type is
  326. // equivalent to another type of the same type.
  327. ////////////////////////////////////////////////////////////////////
  328. bool CPPTypedefType::
  329. is_equal(const CPPDeclaration *other) const {
  330. const CPPTypedefType *ot = ((CPPDeclaration *)other)->as_typedef_type();
  331. assert(ot != NULL);
  332. return (_type == ot->_type) && (*_ident == *ot->_ident);
  333. }
  334. ////////////////////////////////////////////////////////////////////
  335. // Function: CPPTypedefType::is_less
  336. // Access: Protected, Virtual
  337. // Description: Called by CPPDeclaration() to determine whether this type
  338. // should be ordered before another type of the same
  339. // type, in an arbitrary but fixed ordering.
  340. ////////////////////////////////////////////////////////////////////
  341. bool CPPTypedefType::
  342. is_less(const CPPDeclaration *other) const {
  343. return CPPDeclaration::is_less(other);
  344. // The below code causes a crash for unknown reasons.
  345. /*
  346. const CPPTypedefType *ot = ((CPPDeclaration *)other)->as_typedef_type();
  347. assert(ot != NULL);
  348. if (_type != ot->_type) {
  349. return _type < ot->_type;
  350. }
  351. if (*_ident != *ot->_ident) {
  352. return *_ident < *ot->_ident;
  353. }
  354. return false; */
  355. }