ignore .lib and .exe
[prop.git] / prop-src / classdef.cc
blob0adccb58bfbd7dea0a961460a9a1c6f56aa6aa83
1 ///////////////////////////////////////////////////////////////////////////////
2 // This file is generated automatically using Prop (version 2.3.6),
3 // last updated on Nov 2, 1999.
4 // The original source file is "classdef.pcc".
5 ///////////////////////////////////////////////////////////////////////////////
7 #line 1 "classdef.pcc"
8 ///////////////////////////////////////////////////////////////////////////////
9 //
10 // This file implements the class definition mechanism of Prop.
12 ///////////////////////////////////////////////////////////////////////////////
14 #include <iostream>
15 #include <AD/strings/quark.h>
16 #include "ir.h"
17 #include "ast.h"
18 #include "classdef.h"
19 #include "type.h"
20 #include "list.h"
21 #include "hashtab.h"
22 #include "datatype.h"
24 ///////////////////////////////////////////////////////////////////////////////
26 // Names of various class types
28 ///////////////////////////////////////////////////////////////////////////////
29 const char * ClassDefinition::class_type_name[ClassDefinition::LAST_CLASS] =
30 { "datatype",
31 "rewrite class",
32 "syntax class",
33 "inference class",
34 "graphtype",
35 "dataflow class",
36 "datatype subclass",
37 "attributegrammar class",
38 "constraint class",
39 "class"
42 ///////////////////////////////////////////////////////////////////////////////
44 // Hashtable that contains all the classes indexed by name
46 ///////////////////////////////////////////////////////////////////////////////
47 HashTable ClassDefinition::defined_classes(string_hash, string_equal);
49 ClassDefinition * ClassDefinition::lookup_class(CLASS_TYPE ct, Id name)
50 { HashTable::Entry * e = defined_classes.lookup(name);
51 if (e == 0)
52 { error("%L%s %s has not been defined\n", class_type_name[ct], name);
53 return 0;
54 } else
55 { ClassDefinition * C = (ClassDefinition *)(e->v);
56 if (C->class_type != ct && ct != ANY_CLASS)
57 { error("%Lclass %s is not a %s\n"
58 "%!this is where %s %s was previously defined\n",
59 name, class_type_name[ct],
60 C->loc(), class_type_name[C->class_type], name);
61 return 0;
63 return C;
67 void ClassDefinition::insert_class(ClassDefinition * C)
68 { HashTable::Entry * e = defined_classes.lookup(C->class_name);
69 if (e)
70 { ClassDefinition * old_def = (ClassDefinition*)(e->v);
71 error("%Lredefinition of %s %s\n"
72 "%!this is where it was previously defined.\n",
73 class_type_name[C->class_type], C->class_name,
74 old_def->loc());
75 } else
76 { defined_classes.insert(C->class_name,C);
80 ///////////////////////////////////////////////////////////////////////////////
82 // Constructor and destructors for datatype compiler
84 ///////////////////////////////////////////////////////////////////////////////
85 ClassDefinition::ClassDefinition
86 (CLASS_TYPE ct, Id id,
87 TyVars p, Inherits subclasses, TyQual qual, Decls body)
88 : class_type(ct),
89 class_name(id), parameters(p), inherited_classes(subclasses),
90 qualifiers(qual), class_body(body)
91 { constructor_code =
92 #line 84 "classdef.pcc"
93 #line 84 "classdef.pcc"
94 nil_1_
95 #line 84 "classdef.pcc"
96 #line 84 "classdef.pcc"
98 destructor_code =
99 #line 85 "classdef.pcc"
100 #line 85 "classdef.pcc"
101 nil_1_
102 #line 85 "classdef.pcc"
103 #line 85 "classdef.pcc"
105 insert_class(this);
108 ClassDefinition::~ClassDefinition() {}
110 ///////////////////////////////////////////////////////////////////////////////
112 // Method to generate a class definition
114 ///////////////////////////////////////////////////////////////////////////////
115 void ClassDefinition::gen_class_definition(CodeGen& C)
116 { gen_class_predefinition(C);
117 C.pr ("%^%Hclass %s", parameters, class_name);
118 if (inherited_classes !=
119 #line 99 "classdef.pcc"
120 #line 99 "classdef.pcc"
121 nil_1_
122 #line 99 "classdef.pcc"
123 #line 99 "classdef.pcc"
124 ) C.pr (" : %I",inherited_classes);
125 C.pr (" {%+\n");
126 gen_class_interface(C);
127 C.pr ("%&%-%^};\n", class_body);
128 gen_class_postdefinition(C);
131 ///////////////////////////////////////////////////////////////////////////////
133 // The default is to generate nothing for the following
135 ///////////////////////////////////////////////////////////////////////////////
136 void ClassDefinition::gen_class_predefinition(CodeGen& C) {}
137 void ClassDefinition::gen_class_interface(CodeGen& C) {}
138 void ClassDefinition::gen_class_postdefinition(CodeGen& C) {}
139 void ClassDefinition::gen_class_implementation(CodeGen& C, Tys, DefKind) {}
141 ///////////////////////////////////////////////////////////////////////////////
143 // Useful methods
145 ///////////////////////////////////////////////////////////////////////////////
146 Id ClassDefinition::mangled_name() const { return mangle(class_name); }
147 Bool ClassDefinition::is_polymorphic() const { return parameters !=
148 #line 122 "classdef.pcc"
149 #line 122 "classdef.pcc"
150 nil_1_
151 #line 122 "classdef.pcc"
152 #line 122 "classdef.pcc"
153 ; }
154 Bool ClassDefinition::is_view() const { return qualifiers & QUALview; }
156 ///////////////////////////////////////////////////////////////////////////////
158 // Method to add a base class to the inheritance list
160 ///////////////////////////////////////////////////////////////////////////////
161 void ClassDefinition::add_base_class (Id name, Scope s, TyQual q)
163 inherited_classes = add_inherit(name,
164 #line 132 "classdef.pcc"
165 #line 132 "classdef.pcc"
166 nil_1_
167 #line 132 "classdef.pcc"
168 #line 132 "classdef.pcc"
169 ,inherited_classes,s,q);
172 void ClassDefinition::append_base_class (Id name, Scope s, TyQual q)
174 inherited_classes = append(inherited_classes,
175 add_inherit(name,
176 #line 138 "classdef.pcc"
177 #line 138 "classdef.pcc"
178 nil_1_
179 #line 138 "classdef.pcc"
180 #line 138 "classdef.pcc"
182 #line 138 "classdef.pcc"
183 #line 138 "classdef.pcc"
184 nil_1_
185 #line 138 "classdef.pcc"
186 #line 138 "classdef.pcc"
187 ,s,q));
190 ///////////////////////////////////////////////////////////////////////////////
192 // Method to generate a constructor
194 ///////////////////////////////////////////////////////////////////////////////
195 void ClassDefinition::gen_class_constructor(CodeGen& C, Tys tys, DefKind k)
197 switch (k)
198 { case INTERFACE_DEFINITION:
199 C.pr("%^%s ", class_name); break;
200 case INLINE_IMPLEMENTATION:
201 C.pr("%^inline %s ", class_name); break;
202 case EXTERNAL_IMPLEMENTATION:
203 C.pr("%^%H %s%V::%s ",parameters, class_name, parameters, class_name);
204 break;
205 case EXTERNAL_INSTANTIATION:
206 case EXTERNAL_DEFINITION:
207 C.pr("%^%s%P::%s ", class_name, tys, class_name);
208 break;
211 gen_class_constructor_parameters(C, tys, k);
213 switch (k)
214 { case INLINE_IMPLEMENTATION:
215 case EXTERNAL_IMPLEMENTATION:
216 case EXTERNAL_INSTANTIATION:
217 gen_class_constructor_initializers(C, tys, k);
218 C.pr("%^{%+");
219 gen_class_constructor_body(C, tys, k);
220 if (constructor_code) C.pr("%^%&", constructor_code);
221 C.pr("%-%^}");
222 break;
223 case INTERFACE_DEFINITION:
224 case EXTERNAL_DEFINITION:
225 C.pr(";"); break;
229 ///////////////////////////////////////////////////////////////////////////////
231 // Method to generate a destructor
233 ///////////////////////////////////////////////////////////////////////////////
234 void ClassDefinition::gen_class_destructor(CodeGen& C, Tys tys, DefKind k)
236 Id v = (qualifiers & QUALvirtualdestr) ? "virtual " : "";
237 switch (k)
238 { case INTERFACE_DEFINITION:
239 C.pr("%^%s~%s()", v, class_name); break;
240 case INLINE_IMPLEMENTATION:
241 C.pr("%^inline %s~%s()", v, class_name); break;
242 case EXTERNAL_IMPLEMENTATION:
243 C.pr("%^%H %s%V::~%s()",
244 parameters, class_name, parameters, class_name);
245 break;
246 case EXTERNAL_INSTANTIATION:
247 case EXTERNAL_DEFINITION:
248 C.pr("%^%s%P::~%s()", class_name, tys, class_name);
249 break;
252 switch (k)
253 { case INLINE_IMPLEMENTATION:
254 case EXTERNAL_IMPLEMENTATION:
255 case EXTERNAL_INSTANTIATION:
256 C.pr("%^{%+");
257 gen_class_destructor_body(C,tys,k);
258 if (destructor_code) C.pr("%^%&", destructor_code);
259 C.pr("%-%^}");
260 break;
261 case INTERFACE_DEFINITION:
262 case EXTERNAL_DEFINITION:
263 C.pr(";"); break;
267 ///////////////////////////////////////////////////////////////////////////////
269 // Defaults method to generate various parts of the constructor and destructor
271 ///////////////////////////////////////////////////////////////////////////////
272 void ClassDefinition::gen_class_constructor_parameters(CodeGen& C,Tys,DefKind)
273 { C.pr("()");
275 void ClassDefinition::gen_class_constructor_initializers(CodeGen&,Tys,DefKind)
278 void ClassDefinition::gen_class_constructor_body(CodeGen&,Tys,DefKind)
281 void ClassDefinition::gen_class_destructor_body(CodeGen&,Tys,DefKind)
285 ///////////////////////////////////////////////////////////////////////////////
287 // Method to add constructor code to a class
289 ///////////////////////////////////////////////////////////////////////////////
290 ClassDefinition * ClassDefinition::lookup_class_or_datatype
291 (Id class_name, Id constructor)
293 #line 243 "classdef.pcc"
294 #line 250 "classdef.pcc"
296 Ty _V1 = lookup_ty(class_name);
297 if (_V1) {
298 switch (_V1->tag__) {
299 case a_Ty::tag_TYCONty: {
300 if (boxed(((Ty_TYCONty *)_V1)->_1)) {
301 switch (((Ty_TYCONty *)_V1)->_1->tag__) {
302 case a_TyCon::tag_DATATYPEtycon: {
303 if (
304 #line 244 "classdef.pcc"
305 (class_name == constructor)
306 #line 244 "classdef.pcc"
309 #line 245 "classdef.pcc"
310 return ((TyCon_DATATYPEtycon *)((Ty_TYCONty *)_V1)->_1)->hierarchy;
311 #line 245 "classdef.pcc"
312 } else {
314 #line 247 "classdef.pcc"
315 Cons cons = lookup_cons(constructor);
316 if (cons) return cons->class_def;
318 #line 249 "classdef.pcc"
320 } break;
321 default: {
322 L1:;
323 #line 250 "classdef.pcc"
324 return lookup_class(ANY_CLASS,class_name);
325 #line 250 "classdef.pcc"
326 } break;
328 } else { goto L1; }
329 } break;
330 default: { goto L1; } break;
332 } else { goto L1; }
334 #line 251 "classdef.pcc"
335 #line 251 "classdef.pcc"
337 return 0;
340 ///////////////////////////////////////////////////////////////////////////////
342 // Method to add constructor code to a class
344 ///////////////////////////////////////////////////////////////////////////////
345 void ClassDefinition::add_constructor_code
346 (Id class_name, Id constructor, Decls body)
347 { ClassDefinition * C = lookup_class_or_datatype(class_name,constructor);
348 if (C) C->constructor_code = append(C->constructor_code, body);
351 ///////////////////////////////////////////////////////////////////////////////
353 // Method to add destructor code to a class
355 ///////////////////////////////////////////////////////////////////////////////
356 void ClassDefinition::add_destructor_code
357 (Id class_name, Id destructor, Decls body)
358 { ClassDefinition * C = lookup_class_or_datatype(class_name,destructor);
359 if (C) C->destructor_code = append(C->destructor_code, body);
361 #line 276 "classdef.pcc"
363 ------------------------------- Statistics -------------------------------
364 Merge matching rules = yes
365 Number of DFA nodes merged = 23
366 Number of ifs generated = 3
367 Number of switches generated = 2
368 Number of labels = 1
369 Number of gotos = 3
370 Adaptive matching = enabled
371 Fast string matching = disabled
372 Inline downcasts = enabled
373 --------------------------------------------------------------------------