source: src/SynTree/Statement.h@ 4a60488

ADT arm-eh ast-experimental enum forall-pointer-decay jacob/cs343-translation new-ast new-ast-unique-expr pthread-emulation qualifiedEnum
Last change on this file since 4a60488 was c570806, checked in by Michael Brooks <mlbrooks@…>, 6 years ago

Changing new AST's ImplicitCtorDtorStatement to _own_ its reference to the underlying ctor/dtor call statement.

This change fixes a new-AST-resolver bug in which bootloader output lacks constructor/destructor calls surrounding overt declarations. (Constructor/destructor calls on temporaries were already working.)

This fix addresses the last bootloader output difference: now new-AST's bootloader output equals old AST's.

ImplicitCtorDtorStatement's reference to the underlying ctor/dtor call statement changes from readonly<...> to ptr<...>. Accordingly, the visitor framework changes, now proceeding across this reference. Old-AST deletes across this reference on ~ImplicitCtorDtorStatement and old-AST's visitor framework proceeds across this reference. Old AST's declaration of this reference had an incorrect comment saying the reference was non-owning; adjusting this comment.

Future issues with the ownership details of this reference may occur, e.g. when trying to port FixInit to new-AST. In the new-AST modeling, we need to ensure that re-parenting works properly, i.e. we don't delete in a transition state where the ref count falls to zero. The lifecycle of the underlying ctor/dtor statement is only partially understood. I believe, but have only partly tested, that for overt declarations:

This change has been tested for a clean convert-convert difference (vs no new-AST at all), for convert-convert at: pre-resolve, post-resolve, post-parse.

This change has been tested for, and causes a small regression of, cfa-cpp speed of compiling bootloader. Old AST = 4.72 s, New AST before this change = 3.74 s, New ast after this change 3.79 s. All numbers are mean of middle 3, among 5 samples, with 5-sample SDs <= 0.16 sec and mid-3 SDs <= 0.012 sec. New-AST improvement before this fix = 20.8%, new-AST improvement after this fix = 19.7%, a loss of 5.3% of the improvement.

The performance loss makes sense because more constructor calls are being exposed to the resolver. Constructor calls are generally most expensive to resolve, because of their high number of function-name matches.

  • Property mode set to 100644
File size: 19.6 KB
Line 
1//
2// Cforall Version 1.0.0 Copyright (C) 2015 University of Waterloo
3//
4// The contents of this file are covered under the licence agreement in the
5// file "LICENCE" distributed with Cforall.
6//
7// Statement.h --
8//
9// Author : Richard C. Bilson
10// Created On : Mon May 18 07:44:20 2015
11// Last Modified By : Peter A. Buhr
12// Last Modified On : Tue Mar 12 09:01:53 2019
13// Update Count : 83
14//
15
16#pragma once
17
18#include <iosfwd> // for ostream
19#include <list> // for list
20#include <memory> // for allocator
21#include <vector> // for vector
22
23#include "BaseSyntaxNode.h" // for BaseSyntaxNode
24#include "Common/SemanticError.h" // for SemanticError
25#include "Label.h" // for Label
26#include "Mutator.h" // for Mutator
27#include "Visitor.h" // for Visitor
28
29class CatchStmt;
30class ConstantExpr;
31class Declaration;
32class Expression;
33class FinallyStmt;
34
35class Statement : public BaseSyntaxNode {
36 public:
37 std::list<Label> labels;
38
39 Statement( const std::list<Label> & labels = {} );
40 virtual ~Statement();
41
42 std::list<Label> & get_labels() { return labels; }
43 const std::list<Label> & get_labels() const { return labels; }
44
45 virtual Statement * clone() const override = 0;
46 virtual void accept( Visitor & v ) override = 0;
47 virtual void accept( Visitor & v ) const override = 0;
48 virtual Statement * acceptMutator( Mutator & m ) override = 0;
49 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
50};
51
52class CompoundStmt : public Statement {
53 public:
54 std::list<Statement*> kids;
55
56 CompoundStmt();
57 CompoundStmt( std::list<Statement *> stmts );
58 CompoundStmt( const CompoundStmt & other );
59 virtual ~CompoundStmt();
60
61 std::list<Statement*>& get_kids() { return kids; }
62 void push_back( Statement * stmt ) { kids.push_back( stmt ); }
63 void push_front( Statement * stmt ) { kids.push_front( stmt ); }
64
65 virtual CompoundStmt * clone() const override { return new CompoundStmt( *this ); }
66 virtual void accept( Visitor & v ) override { v.visit( this ); }
67 virtual void accept( Visitor & v ) const override { v.visit( this ); }
68 virtual CompoundStmt * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
69 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
70};
71
72class NullStmt : public Statement {
73 public:
74 NullStmt( const std::list<Label> & labels = {} );
75
76 virtual NullStmt * clone() const override { return new NullStmt( *this ); }
77 virtual void accept( Visitor & v ) override { v.visit( this ); }
78 virtual void accept( Visitor & v ) const override { v.visit( this ); }
79 virtual NullStmt * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
80 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
81};
82
83class ExprStmt : public Statement {
84 public:
85 Expression * expr;
86
87 ExprStmt( Expression * expr );
88 ExprStmt( const ExprStmt & other );
89 virtual ~ExprStmt();
90
91 Expression * get_expr() { return expr; }
92 void set_expr( Expression * newValue ) { expr = newValue; }
93
94 virtual ExprStmt * clone() const override { return new ExprStmt( *this ); }
95 virtual void accept( Visitor & v ) override { v.visit( this ); }
96 virtual void accept( Visitor & v ) const override { v.visit( this ); }
97 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
98 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
99};
100
101class AsmStmt : public Statement {
102 public:
103 bool voltile;
104 Expression * instruction;
105 std::list<Expression *> output, input;
106 std::list<ConstantExpr *> clobber;
107 std::list<Label> gotolabels;
108
109 AsmStmt( bool voltile, Expression * instruction, std::list<Expression *> output, std::list<Expression *> input, std::list<ConstantExpr *> clobber, std::list<Label> gotolabels );
110 AsmStmt( const AsmStmt & other );
111 virtual ~AsmStmt();
112
113 bool get_voltile() { return voltile; }
114 void set_voltile( bool newValue ) { voltile = newValue; }
115 Expression * get_instruction() { return instruction; }
116 void set_instruction( Expression * newValue ) { instruction = newValue; }
117 std::list<Expression *> & get_output() { return output; }
118 void set_output( const std::list<Expression *> & newValue ) { output = newValue; }
119 std::list<Expression *> & get_input() { return input; }
120 void set_input( const std::list<Expression *> & newValue ) { input = newValue; }
121 std::list<ConstantExpr *> & get_clobber() { return clobber; }
122 void set_clobber( const std::list<ConstantExpr *> & newValue ) { clobber = newValue; }
123 std::list<Label> & get_gotolabels() { return gotolabels; }
124 void set_gotolabels( const std::list<Label> & newValue ) { gotolabels = newValue; }
125
126 virtual AsmStmt * clone() const override { return new AsmStmt( *this ); }
127 virtual void accept( Visitor & v ) override { v.visit( this ); }
128 virtual void accept( Visitor & v ) const override { v.visit( this ); }
129 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
130 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
131};
132
133class DirectiveStmt : public Statement {
134 public:
135 std::string directive;
136
137 DirectiveStmt( const std::string & );
138 virtual ~DirectiveStmt(){}
139
140 virtual DirectiveStmt * clone() const override { return new DirectiveStmt( *this ); }
141 virtual void accept( Visitor & v ) override { v.visit( this ); }
142 virtual void accept( Visitor & v ) const override { v.visit( this ); }
143 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
144 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
145};
146
147class IfStmt : public Statement {
148 public:
149 Expression * condition;
150 Statement * thenPart;
151 Statement * elsePart;
152 std::list<Statement *> initialization;
153
154 IfStmt( Expression * condition, Statement * thenPart, Statement * elsePart,
155 std::list<Statement *> initialization = std::list<Statement *>() );
156 IfStmt( const IfStmt & other );
157 virtual ~IfStmt();
158
159 std::list<Statement *> & get_initialization() { return initialization; }
160 Expression * get_condition() { return condition; }
161 void set_condition( Expression * newValue ) { condition = newValue; }
162 Statement * get_thenPart() { return thenPart; }
163 void set_thenPart( Statement * newValue ) { thenPart = newValue; }
164 Statement * get_elsePart() { return elsePart; }
165 void set_elsePart( Statement * newValue ) { elsePart = newValue; }
166
167 virtual IfStmt * clone() const override { return new IfStmt( *this ); }
168 virtual void accept( Visitor & v ) override { v.visit( this ); }
169 virtual void accept( Visitor & v ) const override { v.visit( this ); }
170 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
171 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
172};
173
174class SwitchStmt : public Statement {
175 public:
176 Expression * condition;
177 std::list<Statement *> statements;
178
179 SwitchStmt( Expression * condition, const std::list<Statement *> & statements );
180 SwitchStmt( const SwitchStmt & other );
181 virtual ~SwitchStmt();
182
183 Expression * get_condition() { return condition; }
184 void set_condition( Expression * newValue ) { condition = newValue; }
185
186 std::list<Statement *> & get_statements() { return statements; }
187
188 virtual void accept( Visitor & v ) override { v.visit( this ); }
189 virtual void accept( Visitor & v ) const override { v.visit( this ); }
190 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
191
192 virtual SwitchStmt * clone() const override { return new SwitchStmt( *this ); }
193 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
194
195};
196
197class CaseStmt : public Statement {
198 public:
199 Expression * condition;
200 std::list<Statement *> stmts;
201
202 CaseStmt( Expression * conditions, const std::list<Statement *> & stmts, bool isdef = false ) throw (SemanticErrorException);
203 CaseStmt( const CaseStmt & other );
204 virtual ~CaseStmt();
205
206 static CaseStmt * makeDefault( const std::list<Label> & labels = {}, std::list<Statement *> stmts = std::list<Statement *>() );
207
208 bool isDefault() const { return _isDefault; }
209 void set_default(bool b) { _isDefault = b; }
210
211 Expression * & get_condition() { return condition; }
212 void set_condition( Expression * newValue ) { condition = newValue; }
213
214 std::list<Statement *> & get_statements() { return stmts; }
215 void set_statements( std::list<Statement *> & newValue ) { stmts = newValue; }
216
217 virtual void accept( Visitor & v ) override { v.visit( this ); }
218 virtual void accept( Visitor & v ) const override { v.visit( this ); }
219 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
220
221 virtual CaseStmt * clone() const override { return new CaseStmt( *this ); }
222 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
223 private:
224 bool _isDefault;
225};
226
227class WhileStmt : public Statement {
228 public:
229 Expression * condition;
230 Statement * body;
231 std::list<Statement *> initialization;
232 bool isDoWhile;
233
234 WhileStmt( Expression * condition, Statement * body, std::list<Statement *> & initialization, bool isDoWhile = false );
235 WhileStmt( const WhileStmt & other );
236 virtual ~WhileStmt();
237
238 Expression * get_condition() { return condition; }
239 void set_condition( Expression * newValue ) { condition = newValue; }
240 Statement * get_body() { return body; }
241 void set_body( Statement * newValue ) { body = newValue; }
242 bool get_isDoWhile() { return isDoWhile; }
243 void set_isDoWhile( bool newValue ) { isDoWhile = newValue; }
244
245 virtual WhileStmt * clone() const override { return new WhileStmt( *this ); }
246 virtual void accept( Visitor & v ) override { v.visit( this ); }
247 virtual void accept( Visitor & v ) const override { v.visit( this ); }
248 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
249 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
250};
251
252class ForStmt : public Statement {
253 public:
254 std::list<Statement *> initialization;
255 Expression * condition;
256 Expression * increment;
257 Statement * body;
258
259 ForStmt( std::list<Statement *> initialization, Expression * condition = 0, Expression * increment = 0, Statement * body = 0 );
260 ForStmt( const ForStmt & other );
261 virtual ~ForStmt();
262
263 std::list<Statement *> & get_initialization() { return initialization; }
264 Expression * get_condition() { return condition; }
265 void set_condition( Expression * newValue ) { condition = newValue; }
266 Expression * get_increment() { return increment; }
267 void set_increment( Expression * newValue ) { increment = newValue; }
268 Statement * get_body() { return body; }
269 void set_body( Statement * newValue ) { body = newValue; }
270
271 virtual ForStmt * clone() const override { return new ForStmt( *this ); }
272 virtual void accept( Visitor & v ) override { v.visit( this ); }
273 virtual void accept( Visitor & v ) const override { v.visit( this ); }
274 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
275 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
276};
277
278class BranchStmt : public Statement {
279 public:
280 enum Type { Goto = 0, Break, Continue, FallThrough, FallThroughDefault };
281
282 // originalTarget kept for error messages.
283 const Label originalTarget;
284 Label target;
285 Expression * computedTarget;
286 Type type;
287
288 BranchStmt( Label target, Type ) throw (SemanticErrorException);
289 BranchStmt( Expression * computedTarget, Type ) throw (SemanticErrorException);
290
291 Label get_originalTarget() { return originalTarget; }
292 Label get_target() { return target; }
293 void set_target( Label newValue ) { target = newValue; }
294
295 Expression * get_computedTarget() { return computedTarget; }
296 void set_target( Expression * newValue ) { computedTarget = newValue; }
297
298 Type get_type() { return type; }
299 const char * get_typename() { return brType[ type ]; }
300
301 virtual BranchStmt * clone() const override { return new BranchStmt( *this ); }
302 virtual void accept( Visitor & v ) override { v.visit( this ); }
303 virtual void accept( Visitor & v ) const override { v.visit( this ); }
304 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
305 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
306 private:
307 static const char * brType[];
308};
309
310class ReturnStmt : public Statement {
311 public:
312 Expression * expr;
313
314 ReturnStmt( Expression * expr );
315 ReturnStmt( const ReturnStmt & other );
316 virtual ~ReturnStmt();
317
318 Expression * get_expr() { return expr; }
319 void set_expr( Expression * newValue ) { expr = newValue; }
320
321 virtual ReturnStmt * clone() const override { return new ReturnStmt( *this ); }
322 virtual void accept( Visitor & v ) override { v.visit( this ); }
323 virtual void accept( Visitor & v ) const override { v.visit( this ); }
324 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
325 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
326};
327
328class ThrowStmt : public Statement {
329 public:
330 enum Kind { Terminate, Resume };
331
332 const Kind kind;
333 Expression * expr;
334 Expression * target;
335
336 ThrowStmt( Kind kind, Expression * expr, Expression * target = nullptr );
337 ThrowStmt( const ThrowStmt & other );
338 virtual ~ThrowStmt();
339
340 Kind get_kind() { return kind; }
341 Expression * get_expr() { return expr; }
342 void set_expr( Expression * newExpr ) { expr = newExpr; }
343 Expression * get_target() { return target; }
344 void set_target( Expression * newTarget ) { target = newTarget; }
345
346 virtual ThrowStmt * clone() const override { return new ThrowStmt( *this ); }
347 virtual void accept( Visitor & v ) override { v.visit( this ); }
348 virtual void accept( Visitor & v ) const override { v.visit( this ); }
349 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
350 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
351};
352
353class TryStmt : public Statement {
354 public:
355 CompoundStmt * block;
356 std::list<CatchStmt *> handlers;
357 FinallyStmt * finallyBlock;
358
359 TryStmt( CompoundStmt * tryBlock, std::list<CatchStmt *> & handlers, FinallyStmt * finallyBlock = 0 );
360 TryStmt( const TryStmt & other );
361 virtual ~TryStmt();
362
363 CompoundStmt * get_block() const { return block; }
364 void set_block( CompoundStmt * newValue ) { block = newValue; }
365 std::list<CatchStmt *>& get_catchers() { return handlers; }
366
367 FinallyStmt * get_finally() const { return finallyBlock; }
368 void set_finally( FinallyStmt * newValue ) { finallyBlock = newValue; }
369
370 virtual TryStmt * clone() const override { return new TryStmt( *this ); }
371 virtual void accept( Visitor & v ) override { v.visit( this ); }
372 virtual void accept( Visitor & v ) const override { v.visit( this ); }
373 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
374 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
375};
376
377class CatchStmt : public Statement {
378 public:
379 enum Kind { Terminate, Resume };
380
381 const Kind kind;
382 Declaration * decl;
383 Expression * cond;
384 Statement * body;
385
386 CatchStmt( Kind kind, Declaration * decl,
387 Expression * cond, Statement * body );
388 CatchStmt( const CatchStmt & other );
389 virtual ~CatchStmt();
390
391 Kind get_kind() { return kind; }
392 Declaration * get_decl() { return decl; }
393 void set_decl( Declaration * newValue ) { decl = newValue; }
394 Expression * get_cond() { return cond; }
395 void set_cond( Expression * newCond ) { cond = newCond; }
396 Statement * get_body() { return body; }
397 void set_body( Statement * newValue ) { body = newValue; }
398
399 virtual CatchStmt * clone() const override { return new CatchStmt( *this ); }
400 virtual void accept( Visitor & v ) override { v.visit( this ); }
401 virtual void accept( Visitor & v ) const override { v.visit( this ); }
402 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
403 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
404};
405
406class FinallyStmt : public Statement {
407 public:
408 CompoundStmt * block;
409
410 FinallyStmt( CompoundStmt * block );
411 FinallyStmt( const FinallyStmt & other );
412 virtual ~FinallyStmt();
413
414 CompoundStmt * get_block() const { return block; }
415 void set_block( CompoundStmt * newValue ) { block = newValue; }
416
417 virtual FinallyStmt * clone() const override { return new FinallyStmt( *this ); }
418 virtual void accept( Visitor & v ) override { v.visit( this ); }
419 virtual void accept( Visitor & v ) const override { v.visit( this ); }
420 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
421 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
422};
423
424class WaitForStmt : public Statement {
425 public:
426
427 struct Target {
428 Expression * function;
429 std::list<Expression * > arguments;
430 };
431
432 struct Clause {
433 Target target;
434 Statement * statement;
435 Expression * condition;
436 };
437
438 WaitForStmt();
439 WaitForStmt( const WaitForStmt & );
440 virtual ~WaitForStmt();
441
442 std::vector<Clause> clauses;
443
444 struct {
445 Expression * time;
446 Statement * statement;
447 Expression * condition;
448 } timeout;
449
450 struct {
451 Statement * statement;
452 Expression * condition;
453 } orelse;
454
455 virtual WaitForStmt * clone() const override { return new WaitForStmt( *this ); }
456 virtual void accept( Visitor & v ) override { v.visit( this ); }
457 virtual void accept( Visitor & v ) const override { v.visit( this ); }
458 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
459 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
460
461};
462
463// class WithStmt : public Statement {
464// public:
465// std::list< Expression * > exprs;
466// Statement * stmt;
467
468// WithStmt( const std::list< Expression * > & exprs, Statement * stmt );
469// WithStmt( const WithStmt & other );
470// virtual ~WithStmt();
471
472// virtual WithStmt * clone() const override { return new WithStmt( *this ); }
473// virtual void accept( Visitor & v ) override { v.visit( this ); }
474// virtual void accept( Visitor & v ) const override { v.visit( this ); }
475// virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
476// virtual void print( std::ostream & os, Indenter indent = {} ) const override;
477// };
478
479
480// represents a declaration that occurs as part of a compound statement
481class DeclStmt : public Statement {
482 public:
483 Declaration * decl;
484
485 DeclStmt( Declaration * decl );
486 DeclStmt( const DeclStmt & other );
487 virtual ~DeclStmt();
488
489 Declaration * get_decl() const { return decl; }
490 void set_decl( Declaration * newValue ) { decl = newValue; }
491
492 virtual DeclStmt * clone() const override { return new DeclStmt( *this ); }
493 virtual void accept( Visitor & v ) override { v.visit( this ); }
494 virtual void accept( Visitor & v ) const override { v.visit( this ); }
495 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
496 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
497};
498
499
500/// represents an implicit application of a constructor or destructor. Qualifiers are replaced immediately before and
501/// after the call so that qualified objects can be constructed with the same functions as unqualified objects.
502class ImplicitCtorDtorStmt : public Statement {
503 public:
504 // the constructor/destructor call statement; owned here for a while, eventually transferred elsewhere
505 Statement * callStmt;
506
507 ImplicitCtorDtorStmt( Statement * callStmt );
508 ImplicitCtorDtorStmt( const ImplicitCtorDtorStmt & other );
509 virtual ~ImplicitCtorDtorStmt();
510
511 Statement * get_callStmt() const { return callStmt; }
512 void set_callStmt( Statement * newValue ) { callStmt = newValue; }
513
514 virtual ImplicitCtorDtorStmt * clone() const override { return new ImplicitCtorDtorStmt( *this ); }
515 virtual void accept( Visitor & v ) override { v.visit( this ); }
516 virtual void accept( Visitor & v ) const override { v.visit( this ); }
517 virtual Statement * acceptMutator( Mutator & m ) override { return m.mutate( this ); }
518 virtual void print( std::ostream & os, Indenter indent = {} ) const override;
519};
520
521// Local Variables: //
522// tab-width: 4 //
523// mode: c++ //
524// compile-command: "make install" //
525// End: //
Note: See TracBrowser for help on using the repository browser.