source: translator/GenPoly/Box.cc@ 643a2e1

ADT aaron-thesis arm-eh ast-experimental cleanup-dtors ctor deferred_resn demangler enum forall-pointer-decay gc_noraii jacob/cs343-translation jenkins-sandbox memory new-ast new-ast-unique-expr new-env no_list persistent-indexer pthread-emulation qualifiedEnum resolv-new string with_gc
Last change on this file since 643a2e1 was 6c3744e, checked in by Peter A. Buhr <pabuhr@…>, 11 years ago

add list initializer, formatting changes

  • Property mode set to 100644
File size: 43.1 KB
Line 
1/*
2 * This file is part of the Cforall project
3 *
4 * $Id: Box.cc,v 1.20 2005/08/29 20:14:13 rcbilson Exp $
5 *
6 */
7
8#include <set>
9#include <string>
10#include <iterator>
11#include <algorithm>
12#include <cassert>
13
14#include "Box.h"
15#include "PolyMutator.h"
16#include "FindFunction.h"
17#include "ScrubTyVars.h"
18
19#include "SynTree/Declaration.h"
20#include "SynTree/Type.h"
21#include "SynTree/Expression.h"
22#include "SynTree/Initializer.h"
23#include "SynTree/Statement.h"
24#include "SynTree/Mutator.h"
25#include "ResolvExpr/TypeEnvironment.h"
26#include "SymTab/Mangler.h"
27
28#include "SemanticError.h"
29#include "UniqueName.h"
30#include "utility.h"
31
32#include <ext/functional> // temporary
33
34namespace GenPoly {
35 namespace {
36 const std::list<Label> noLabels;
37
38 class Pass1 : public PolyMutator {
39 public:
40 Pass1();
41 virtual Expression *mutate( ApplicationExpr *appExpr );
42 virtual Expression *mutate( AddressExpr *addrExpr );
43 virtual Expression *mutate( UntypedExpr *expr );
44 virtual DeclarationWithType* mutate( FunctionDecl *functionDecl );
45 virtual TypeDecl *mutate( TypeDecl *typeDecl );
46 virtual Expression *mutate( CommaExpr *commaExpr );
47 virtual Expression *mutate( ConditionalExpr *condExpr );
48 virtual Statement *mutate(ReturnStmt *catchStmt);
49 virtual Type *mutate( PointerType *pointerType );
50 virtual Type *mutate( FunctionType *pointerType );
51
52 virtual void doEndScope();
53 private:
54 void passTypeVars( ApplicationExpr *appExpr, std::list< Expression *>::iterator &arg, const TyVarMap &exprTyVars );
55 Expression *addRetParam( ApplicationExpr *appExpr, FunctionType *function, Type *retType, std::list< Expression *>::iterator &arg );
56 Expression *addPolyRetParam( ApplicationExpr *appExpr, FunctionType *function, std::string typeName, std::list< Expression *>::iterator &arg );
57 Expression *applyAdapter( ApplicationExpr *appExpr, FunctionType *function, std::list< Expression *>::iterator &arg, const TyVarMap &exprTyVars );
58 void boxParam( Type *formal, Expression *&arg, const TyVarMap &exprTyVars );
59 void boxParams( ApplicationExpr *appExpr, FunctionType *function, std::list< Expression *>::iterator &arg, const TyVarMap &exprTyVars );
60 void addInferredParams( ApplicationExpr *appExpr, FunctionType *functionType, std::list< Expression *>::iterator &arg, const TyVarMap &tyVars );
61 void findAssignOps( const std::list< TypeDecl *> &forall );
62 void passAdapters( ApplicationExpr *appExpr, FunctionType *functionType, const TyVarMap &exprTyVars );
63 FunctionDecl *makeAdapter( FunctionType *adaptee, FunctionType *realType, const std::string &mangleName, const TyVarMap &tyVars );
64 Expression *handleIntrinsics( ApplicationExpr *appExpr );
65 ObjectDecl *makeTemporary( Type *type );
66
67 std::map< std::string, DeclarationWithType *> assignOps;
68 std::map< std::string, FunctionDecl *> adapters;
69 DeclarationWithType *retval;
70 bool useRetval;
71 UniqueName tempNamer;
72 };
73
74 class Pass2 : public PolyMutator {
75 public:
76 Pass2();
77 template< typename DeclClass >
78 DeclClass *handleDecl( DeclClass *decl, Type *type );
79 virtual DeclarationWithType *mutate( FunctionDecl *functionDecl );
80 virtual ObjectDecl *mutate( ObjectDecl *objectDecl );
81 virtual TypeDecl *mutate( TypeDecl *typeDecl );
82 virtual TypedefDecl *mutate( TypedefDecl *typedefDecl );
83 virtual Type *mutate( PointerType *pointerType );
84 virtual Type *mutate( FunctionType *funcType );
85 private:
86 void addAdapters( FunctionType *functionType );
87
88 std::map< UniqueId, std::string > adapterName;
89 };
90
91 class Pass3 : public PolyMutator {
92 public:
93 template< typename DeclClass >
94 DeclClass *handleDecl( DeclClass *decl, Type *type );
95 virtual DeclarationWithType *mutate( FunctionDecl *functionDecl );
96 virtual ObjectDecl *mutate( ObjectDecl *objectDecl );
97 virtual TypedefDecl *mutate( TypedefDecl *objectDecl );
98 virtual TypeDecl *mutate( TypeDecl *objectDecl );
99 virtual Statement *mutate( DeclStmt *declStmt );
100 virtual Type *mutate( PointerType *pointerType );
101 virtual Type *mutate( FunctionType *funcType );
102 private:
103 };
104
105 } // anonymous namespace
106
107 void printAllNotBuiltin( const std::list< Declaration *>& translationUnit, std::ostream &os ) {
108 for ( std::list< Declaration *>::const_iterator i = translationUnit.begin(); i != translationUnit.end(); ++i ) {
109 if ( !LinkageSpec::isBuiltin( (*i)->get_linkage() ) ) {
110 (*i)->print( os );
111 os << std::endl;
112 } // if
113 } // for
114 }
115
116 void box( std::list< Declaration *>& translationUnit ) {
117 Pass1 pass1;
118 Pass2 pass2;
119 Pass3 pass3;
120 mutateAll( translationUnit, pass1 );
121 mutateAll( translationUnit, pass2 );
122 mutateAll( translationUnit, pass3 );
123 }
124
125////////////////////////////////////////// Pass1 ////////////////////////////////////////////////////
126
127 namespace {
128 bool isPolyRet( FunctionType *function, std::string &name, const TyVarMap &otherTyVars ) {
129 bool doTransform = false;
130 if ( !function->get_returnVals().empty() ) {
131 if ( TypeInstType *typeInst = dynamic_cast< TypeInstType *>( function->get_returnVals().front()->get_type() ) ) {
132
133 // figure out if the return type is specified by a type parameter
134 for ( std::list< TypeDecl *>::const_iterator tyVar = function->get_forall().begin(); tyVar != function->get_forall().end(); ++tyVar ) {
135 if ( (*tyVar)->get_name() == typeInst->get_name() ) {
136 doTransform = true;
137 name = typeInst->get_name();
138 break;
139 } // if
140 } // for
141 if ( !doTransform && otherTyVars.find( typeInst->get_name() ) != otherTyVars.end() ) {
142 doTransform = true;
143 } // if
144 } // if
145 } // if
146 return doTransform;
147 }
148
149 bool isPolyRet( FunctionType *function, std::string &name ) {
150 TyVarMap dummyTyVars;
151 return isPolyRet( function, name, dummyTyVars );
152 }
153
154 Pass1::Pass1()
155 : useRetval( false ), tempNamer( "_temp" ) {
156 }
157
158 bool checkAssignment( DeclarationWithType *decl, std::string &name ) {
159 if ( decl->get_name() == "?=?" ) {
160 if ( PointerType *ptrType = dynamic_cast< PointerType *>( decl->get_type() ) ) {
161 if ( FunctionType *funType = dynamic_cast< FunctionType *>( ptrType->get_base() ) ) {
162 if ( funType->get_parameters().size() == 2 ) {
163 if ( PointerType *pointer = dynamic_cast< PointerType *>( funType->get_parameters().front()->get_type() ) ) {
164 if ( TypeInstType *typeInst = dynamic_cast< TypeInstType *>( pointer->get_base() ) ) {
165 name = typeInst->get_name();
166 return true;
167 } // if
168 } // if
169 } // if
170 } // if
171 } // if
172 } // if
173 return false;
174 }
175
176 void Pass1::findAssignOps( const std::list< TypeDecl *> &forall ) {
177 assignOps.clear();
178 for ( std::list< TypeDecl *>::const_iterator i = forall.begin(); i != forall.end(); ++i ) {
179 for ( std::list< DeclarationWithType *>::const_iterator assert = (*i)->get_assertions().begin(); assert != (*i)->get_assertions().end(); ++assert ) {
180 std::string typeName;
181 if ( checkAssignment( *assert, typeName ) ) {
182 assignOps[ typeName ] = *assert;
183 } // if
184 } // for
185 } // for
186 }
187
188 DeclarationWithType *
189 Pass1::mutate( FunctionDecl *functionDecl ) {
190 if ( functionDecl->get_statements() ) {
191 TyVarMap oldtyVars = scopeTyVars;
192 DeclarationWithType *oldRetval = retval;
193 bool oldUseRetval = useRetval;
194
195 retval = 0;
196 std::string typeName;
197 if ( isPolyRet( functionDecl->get_functionType(), typeName ) && functionDecl->get_linkage() == LinkageSpec::Cforall ) {
198 retval = functionDecl->get_functionType()->get_returnVals().front();
199
200 // give names to unnamed return values
201 if ( retval->get_name() == "" ) {
202 retval->set_name( "_retparm" );
203 retval->set_linkage( LinkageSpec::C );
204 } // if
205 } // if
206
207 scopeTyVars.clear();
208/// std::cerr << "clear\n";
209 makeTyVarMap( functionDecl->get_functionType(), scopeTyVars );
210 findAssignOps( functionDecl->get_functionType()->get_forall() );
211 functionDecl->set_statements( functionDecl->get_statements()->acceptMutator( *this ) );
212
213 scopeTyVars = oldtyVars;
214/// std::cerr << "end FunctionDecl: ";
215/// for ( TyVarMap::iterator i = scopeTyVars.begin(); i != scopeTyVars.end(); ++i ) {
216/// std::cerr << i->first << " ";
217/// }
218/// std::cerr << "\n";
219 retval = oldRetval;
220 useRetval = oldUseRetval;
221 doEndScope();
222 } // if
223 return functionDecl;
224 }
225
226 TypeDecl *Pass1::mutate( TypeDecl *typeDecl ) {
227/// std::cerr << "add " << typeDecl->get_name() << "\n";
228 scopeTyVars[ typeDecl->get_name() ] = typeDecl->get_kind();
229 return Mutator::mutate( typeDecl );
230 }
231
232 Expression *Pass1::mutate( CommaExpr *commaExpr ) {
233 bool oldUseRetval = useRetval;
234 useRetval = false;
235 commaExpr->set_arg1( maybeMutate( commaExpr->get_arg1(), *this ) );
236 useRetval = oldUseRetval;
237 commaExpr->set_arg2( maybeMutate( commaExpr->get_arg2(), *this ) );
238 return commaExpr;
239 }
240
241 Expression *Pass1::mutate( ConditionalExpr *condExpr ) {
242 bool oldUseRetval = useRetval;
243 useRetval = false;
244 condExpr->set_arg1( maybeMutate( condExpr->get_arg1(), *this ) );
245 useRetval = oldUseRetval;
246 condExpr->set_arg2( maybeMutate( condExpr->get_arg2(), *this ) );
247 condExpr->set_arg3( maybeMutate( condExpr->get_arg3(), *this ) );
248 return condExpr;
249
250 }
251
252 void Pass1::passTypeVars( ApplicationExpr *appExpr, std::list< Expression *>::iterator &arg, const TyVarMap &exprTyVars ) {
253 for ( TyVarMap::const_iterator tyParm = exprTyVars.begin(); tyParm != exprTyVars.end(); ++tyParm ) {
254 ResolvExpr::EqvClass eqvClass;
255 assert( env );
256 if ( tyParm->second == TypeDecl::Any ) {
257 Type *concrete = env->lookup( tyParm->first );
258 if ( concrete ) {
259 arg = appExpr->get_args().insert( arg, new SizeofExpr( concrete->clone() ) );
260 arg++;
261 } else {
262 throw SemanticError( "unbound type variable in application ", appExpr );
263 } // if
264 } // if
265 } // for
266 }
267
268 ObjectDecl *Pass1::makeTemporary( Type *type ) {
269 ObjectDecl *newObj = new ObjectDecl( tempNamer.newName(), Declaration::NoStorageClass, LinkageSpec::C, 0, type, 0 );
270 stmtsToAdd.push_back( new DeclStmt( noLabels, newObj ) );
271 return newObj;
272 }
273
274 TypeInstType *isPolyType( Type *type, const TypeSubstitution *env, const TyVarMap &tyVars ) {
275 if ( TypeInstType *typeInst = dynamic_cast< TypeInstType *>( type ) ) {
276 if ( env ) {
277 if ( Type *newType = env->lookup( typeInst->get_name() ) ) {
278 return isPolyType( newType, env, tyVars );
279 } // if
280 } // if
281 if ( tyVars.find( typeInst->get_name() ) != tyVars.end() ) {
282 return typeInst;
283 } else {
284 return 0;
285 } // if
286 } else {
287 return 0;
288 } // if
289 }
290
291 Expression *Pass1::addRetParam( ApplicationExpr *appExpr, FunctionType *function, Type *retType, std::list< Expression *>::iterator &arg ) {
292 if ( useRetval ) {
293 assert( retval );
294 arg = appExpr->get_args().insert( arg, new VariableExpr( retval ) );
295 arg++;
296 } else {
297 ObjectDecl *newObj = makeTemporary( retType->clone() );
298 Expression *paramExpr = new VariableExpr( newObj );
299 if ( !isPolyType( newObj->get_type(), env, scopeTyVars ) ) {
300 paramExpr = new AddressExpr( paramExpr );
301 } // if
302 arg = appExpr->get_args().insert( arg, paramExpr );
303 arg++;
304/// stmtsToAdd.push_back( new ExprStmt( noLabels, appExpr ) );
305 CommaExpr *commaExpr = new CommaExpr( appExpr, new VariableExpr( newObj ) );
306 commaExpr->set_env( appExpr->get_env() );
307 appExpr->set_env( 0 );
308 return commaExpr;
309 } // if
310 return appExpr;
311 }
312
313 Expression *Pass1::addPolyRetParam( ApplicationExpr *appExpr, FunctionType *function, std::string typeName, std::list< Expression *>::iterator &arg ) {
314 ResolvExpr::EqvClass eqvClass;
315 assert( env );
316 Type *concrete = env->lookup( typeName );
317 if ( concrete == 0 ) {
318 throw SemanticError( "Unbound type variable " + typeName + " in", appExpr );
319 } // if
320 return addRetParam( appExpr, function, concrete, arg );
321 }
322
323 Expression *Pass1::applyAdapter( ApplicationExpr *appExpr, FunctionType *function, std::list< Expression *>::iterator &arg, const TyVarMap &tyVars ) {
324 Expression *ret = appExpr;
325 if ( !function->get_returnVals().empty() && isPolyVal( function->get_returnVals().front()->get_type(), tyVars ) ) {
326 ret = addRetParam( appExpr, function, function->get_returnVals().front()->get_type(), arg );
327 } // if
328 appExpr->get_args().push_front( appExpr->get_function() );
329 appExpr->set_function( new NameExpr( "_adapter" + SymTab::Mangler::mangle( function ) ) );
330
331 return ret;
332 }
333
334 void Pass1::boxParam( Type *param, Expression *&arg, const TyVarMap &exprTyVars ) {
335 assert( !arg->get_results().empty() );
336/// if ( !dynamic_cast< PointerType *>( arg->get_results().front() ) ) {
337 TypeInstType *typeInst = dynamic_cast< TypeInstType *>( param );
338 if ( typeInst && exprTyVars.find( typeInst->get_name() ) != exprTyVars.end() ) {
339 if ( arg->get_results().front()->get_isLvalue() ) {
340 arg = new AddressExpr( arg );
341 } else {
342 ObjectDecl *newObj = new ObjectDecl( tempNamer.newName(), Declaration::NoStorageClass, LinkageSpec::C, 0, arg->get_results().front()->clone(), 0 );
343 newObj->get_type()->get_qualifiers() = Type::Qualifiers();
344 stmtsToAdd.push_back( new DeclStmt( noLabels, newObj ) );
345 UntypedExpr *assign = new UntypedExpr( new NameExpr( "?=?" ) );
346 assign->get_args().push_back( new VariableExpr( newObj ) );
347 assign->get_args().push_back( arg );
348 stmtsToAdd.push_back( new ExprStmt( noLabels, assign ) );
349 arg = new AddressExpr( new VariableExpr( newObj ) );
350 } // if
351 } // if
352/// }
353 }
354
355 void addCast( Expression *&actual, Type *formal, const TyVarMap &tyVars ) {
356 Type *newType = formal->clone();
357 std::list< FunctionType *> functions;
358 // instead of functions needing adapters, this really ought to look for
359 // any function mentioning a polymorphic type
360 findAndReplaceFunction( newType, functions, tyVars, needsAdapter );
361 if ( !functions.empty() ) {
362 actual = new CastExpr( actual, newType );
363 } else {
364 delete newType;
365 } // if
366 }
367
368 void Pass1::boxParams( ApplicationExpr *appExpr, FunctionType *function, std::list< Expression *>::iterator &arg, const TyVarMap &exprTyVars ) {
369/// std::cout << "function is ";
370/// function->print( std::cout );
371 for ( std::list< DeclarationWithType *>::const_iterator param = function->get_parameters().begin(); param != function->get_parameters().end(); ++param, ++arg ) {
372/// std::cout << "parameter is ";
373/// (*param)->print( std::cout );
374/// std::cout << std::endl << "argument is ";
375/// (*arg)->print( std::cout );
376 assert( arg != appExpr->get_args().end() );
377 addCast( *arg, (*param)->get_type(), exprTyVars );
378 boxParam( (*param)->get_type(), *arg, exprTyVars );
379 } // for
380 }
381
382 void Pass1::addInferredParams( ApplicationExpr *appExpr, FunctionType *functionType, std::list< Expression *>::iterator &arg, const TyVarMap &tyVars ) {
383 std::list< Expression *>::iterator cur = arg;
384 for ( std::list< TypeDecl *>::iterator tyVar = functionType->get_forall().begin(); tyVar != functionType->get_forall().end(); ++tyVar ) {
385 for ( std::list< DeclarationWithType *>::iterator assert = (*tyVar)->get_assertions().begin(); assert != (*tyVar)->get_assertions().end(); ++assert ) {
386 InferredParams::const_iterator inferParam = appExpr->get_inferParams().find( (*assert)->get_uniqueId() );
387 assert( inferParam != appExpr->get_inferParams().end() );
388 Expression *newExpr = inferParam->second.expr->clone();
389 addCast( newExpr, (*assert)->get_type(), tyVars );
390 boxParam( (*assert)->get_type(), newExpr, tyVars );
391 appExpr->get_args().insert( cur, newExpr );
392 } // for
393 } // for
394 }
395
396 void makeRetParm( FunctionType *funcType ) {
397 DeclarationWithType *retParm = funcType->get_returnVals().front();
398
399 // make a new parameter that is a pointer to the type of the old return value
400 retParm->set_type( new PointerType( Type::Qualifiers(), retParm->get_type() ) );
401 funcType->get_parameters().push_front( retParm );
402
403 // we don't need the return value any more
404 funcType->get_returnVals().clear();
405 }
406
407 FunctionType *makeAdapterType( FunctionType *adaptee, const TyVarMap &tyVars ) {
408 // actually make the adapter type
409 FunctionType *adapter = adaptee->clone();
410 if ( !adapter->get_returnVals().empty() && isPolyVal( adapter->get_returnVals().front()->get_type(), tyVars ) ) {
411 makeRetParm( adapter );
412 } // if
413 adapter->get_parameters().push_front( new ObjectDecl( "", Declaration::NoStorageClass, LinkageSpec::C, 0, new PointerType( Type::Qualifiers(), new FunctionType( Type::Qualifiers(), true ) ), 0 ) );
414 return adapter;
415 }
416
417 Expression *makeAdapterArg( DeclarationWithType *param, DeclarationWithType *arg, DeclarationWithType *realParam, const TyVarMap &tyVars ) {
418 assert( param );
419 assert( arg );
420/// std::cout << "arg type is ";
421/// arg->get_type()->print( std::cout );
422/// std::cout << "param type is ";
423/// param->get_type()->print( std::cout );
424/// std::cout << " tyVars are: ";
425/// printTyVarMap( std::cout, tyVars );
426 if ( isPolyVal( realParam->get_type(), tyVars ) ) {
427/// if ( dynamic_cast< PointerType *>( arg->get_type() ) ) {
428/// return new CastExpr( new VariableExpr( param ), arg->get_type()->clone() );
429/// } else {
430 UntypedExpr *deref = new UntypedExpr( new NameExpr( "*?" ) );
431 deref->get_args().push_back( new CastExpr( new VariableExpr( param ), new PointerType( Type::Qualifiers(), arg->get_type()->clone() ) ) );
432 deref->get_results().push_back( arg->get_type()->clone() );
433 return deref;
434/// }
435 } // if
436 return new VariableExpr( param );
437 }
438
439 void addAdapterParams( ApplicationExpr *adapteeApp, std::list< DeclarationWithType *>::iterator arg, std::list< DeclarationWithType *>::iterator param, std::list< DeclarationWithType *>::iterator paramEnd, std::list< DeclarationWithType *>::iterator realParam, const TyVarMap &tyVars ) {
440 UniqueName paramNamer( "_p" );
441 for ( ; param != paramEnd; ++param, ++arg, ++realParam ) {
442 if ( (*param)->get_name() == "" ) {
443 (*param)->set_name( paramNamer.newName() );
444 (*param)->set_linkage( LinkageSpec::C );
445 } // if
446 adapteeApp->get_args().push_back( makeAdapterArg( *param, *arg, *realParam, tyVars ) );
447 } // for
448 }
449
450 FunctionDecl *Pass1::makeAdapter( FunctionType *adaptee, FunctionType *realType, const std::string &mangleName, const TyVarMap &tyVars ) {
451 FunctionType *adapterType = makeAdapterType( adaptee, tyVars );
452 adapterType = ScrubTyVars::scrub( adapterType, tyVars );
453 DeclarationWithType *adapteeDecl = adapterType->get_parameters().front();
454 adapteeDecl->set_name( "_adaptee" );
455 ApplicationExpr *adapteeApp = new ApplicationExpr( new CastExpr( new VariableExpr( adapteeDecl ), new PointerType( Type::Qualifiers(), realType ) ) );
456 Statement *bodyStmt;
457
458 std::list< TypeDecl *>::iterator tyArg = realType->get_forall().begin();
459 std::list< TypeDecl *>::iterator tyParam = adapterType->get_forall().begin();
460 std::list< TypeDecl *>::iterator realTyParam = adaptee->get_forall().begin();
461 for ( ; tyParam != adapterType->get_forall().end(); ++tyArg, ++tyParam, ++realTyParam ) {
462 assert( tyArg != realType->get_forall().end() );
463 std::list< DeclarationWithType *>::iterator assertArg = (*tyArg)->get_assertions().begin();
464 std::list< DeclarationWithType *>::iterator assertParam = (*tyParam)->get_assertions().begin();
465 std::list< DeclarationWithType *>::iterator realAssertParam = (*realTyParam)->get_assertions().begin();
466 for ( ; assertParam != (*tyParam)->get_assertions().end(); ++assertArg, ++assertParam, ++realAssertParam ) {
467 assert( assertArg != (*tyArg)->get_assertions().end() );
468 adapteeApp->get_args().push_back( makeAdapterArg( *assertParam, *assertArg, *realAssertParam, tyVars ) );
469 } // for
470 } // for
471
472 std::list< DeclarationWithType *>::iterator arg = realType->get_parameters().begin();
473 std::list< DeclarationWithType *>::iterator param = adapterType->get_parameters().begin();
474 std::list< DeclarationWithType *>::iterator realParam = adaptee->get_parameters().begin();
475 param++; // skip adaptee parameter
476 if ( realType->get_returnVals().empty() ) {
477 addAdapterParams( adapteeApp, arg, param, adapterType->get_parameters().end(), realParam, tyVars );
478 bodyStmt = new ExprStmt( noLabels, adapteeApp );
479 } else if ( isPolyVal( adaptee->get_returnVals().front()->get_type(), tyVars ) ) {
480 if ( (*param)->get_name() == "" ) {
481 (*param)->set_name( "_ret" );
482 (*param)->set_linkage( LinkageSpec::C );
483 } // if
484 UntypedExpr *assign = new UntypedExpr( new NameExpr( "?=?" ) );
485 UntypedExpr *deref = new UntypedExpr( new NameExpr( "*?" ) );
486 deref->get_args().push_back( new CastExpr( new VariableExpr( *param++ ), new PointerType( Type::Qualifiers(), realType->get_returnVals().front()->get_type()->clone() ) ) );
487 assign->get_args().push_back( deref );
488 addAdapterParams( adapteeApp, arg, param, adapterType->get_parameters().end(), realParam, tyVars );
489 assign->get_args().push_back( adapteeApp );
490 bodyStmt = new ExprStmt( noLabels, assign );
491 } else {
492 // adapter for a function that returns a monomorphic value
493 addAdapterParams( adapteeApp, arg, param, adapterType->get_parameters().end(), realParam, tyVars );
494 bodyStmt = new ReturnStmt( noLabels, adapteeApp );
495 } // if
496 CompoundStmt *adapterBody = new CompoundStmt( noLabels );
497 adapterBody->get_kids().push_back( bodyStmt );
498 return new FunctionDecl( "_adapter" + mangleName, Declaration::NoStorageClass, LinkageSpec::C, adapterType, adapterBody, false );
499 }
500
501 void Pass1::passAdapters( ApplicationExpr *appExpr, FunctionType *functionType, const TyVarMap &exprTyVars ) {
502 std::list< DeclarationWithType *> &paramList = functionType->get_parameters();
503 std::list< FunctionType *> functions;
504 for ( std::list< TypeDecl *>::iterator tyVar = functionType->get_forall().begin(); tyVar != functionType->get_forall().end(); ++tyVar ) {
505 for ( std::list< DeclarationWithType *>::iterator assert = (*tyVar)->get_assertions().begin(); assert != (*tyVar)->get_assertions().end(); ++assert ) {
506 findFunction( (*assert)->get_type(), functions, exprTyVars, needsAdapter );
507 } // for
508 } // for
509 for ( std::list< DeclarationWithType *>::iterator arg = paramList.begin(); arg != paramList.end(); ++arg ) {
510 findFunction( (*arg)->get_type(), functions, exprTyVars, needsAdapter );
511 } // for
512 std::set< std::string > adaptersDone;
513 for ( std::list< FunctionType *>::iterator funType = functions.begin(); funType != functions.end(); ++funType ) {
514 FunctionType *realFunction = (*funType)->clone();
515 assert( env );
516 env->apply( realFunction );
517 std::string mangleName = SymTab::Mangler::mangle( realFunction );
518 if ( adaptersDone.find( mangleName ) == adaptersDone.end() ) {
519 std::map< std::string, FunctionDecl *>::iterator adapter = adapters.find( mangleName );
520 if ( adapter == adapters.end() ) {
521 FunctionDecl *newAdapter = makeAdapter( *funType, realFunction, mangleName, exprTyVars );
522 adapter = adapters.insert( adapters.begin(), std::pair< std::string, FunctionDecl *>( mangleName, newAdapter ) );
523 stmtsToAdd.push_back( new DeclStmt( noLabels, newAdapter ) );
524 } // if
525 assert( adapter != adapters.end() );
526 appExpr->get_args().push_front( new VariableExpr( adapter->second ) );
527 adaptersDone.insert( adaptersDone.begin(), mangleName );
528 } // if
529 } // for
530 }
531
532 TypeInstType *isPolyPtr( Type *type, const TypeSubstitution *env, const TyVarMap &tyVars ) {
533 if ( PointerType *ptr = dynamic_cast< PointerType *>( type ) ) {
534 return isPolyType( ptr->get_base(), env, tyVars );
535 } else if ( env ) {
536 if ( TypeInstType *typeInst = dynamic_cast< TypeInstType *>( type ) ) {
537 if ( Type *newType = env->lookup( typeInst->get_name() ) ) {
538 return isPolyPtr( newType, env, tyVars );
539 } // if
540 } // if
541 } // if
542 return 0;
543 }
544
545 TypeInstType *isPolyPtrPtr( Type *type, const TypeSubstitution *env, const TyVarMap &tyVars ) {
546 if ( PointerType *ptr = dynamic_cast< PointerType *>( type ) ) {
547 return isPolyPtr( ptr->get_base(), env, tyVars );
548 } else if ( env ) {
549 if ( TypeInstType *typeInst = dynamic_cast< TypeInstType *>( type ) ) {
550 if ( Type *newType = env->lookup( typeInst->get_name() ) ) {
551 return isPolyPtrPtr( newType, env, tyVars );
552 } // if
553 } // if
554 } // if
555 return 0;
556 }
557
558 Expression *makeIncrDecrExpr( ApplicationExpr *appExpr, std::string polyName, bool isIncr ) {
559 NameExpr *opExpr;
560 if ( isIncr ) {
561 opExpr = new NameExpr( "?+=?" );
562 } else {
563 opExpr = new NameExpr( "?-=?" );
564 } // if
565 UntypedExpr *addAssign = new UntypedExpr( opExpr );
566 if ( AddressExpr *address = dynamic_cast< AddressExpr *>( appExpr->get_args().front() ) ) {
567 addAssign->get_args().push_back( address->get_arg() );
568 } else {
569 addAssign->get_args().push_back( appExpr->get_args().front() );
570 } // if
571 addAssign->get_args().push_back( new NameExpr( polyName ) );
572 addAssign->get_results().front() = appExpr->get_results().front()->clone();
573 if ( appExpr->get_env() ) {
574 addAssign->set_env( appExpr->get_env() );
575 appExpr->set_env( 0 );
576 } // if
577 appExpr->get_args().clear();
578 delete appExpr;
579 return addAssign;
580 }
581
582 Expression *Pass1::handleIntrinsics( ApplicationExpr *appExpr ) {
583 if ( VariableExpr *varExpr = dynamic_cast< VariableExpr *>( appExpr->get_function() ) ) {
584 if ( varExpr->get_var()->get_linkage() == LinkageSpec::Intrinsic ) {
585 if ( varExpr->get_var()->get_name() == "?[?]" ) {
586 assert( !appExpr->get_results().empty() );
587 assert( appExpr->get_args().size() == 2 );
588 TypeInstType *typeInst1 = isPolyPtr( appExpr->get_args().front()->get_results().front(), env, scopeTyVars );
589 TypeInstType *typeInst2 = isPolyPtr( appExpr->get_args().back()->get_results().front(), env, scopeTyVars );
590 assert( !typeInst1 || !typeInst2 );
591 UntypedExpr *ret = 0;
592 if ( typeInst1 || typeInst2 ) {
593 ret = new UntypedExpr( new NameExpr( "?+?" ) );
594 } // if
595 if ( typeInst1 ) {
596 UntypedExpr *multiply = new UntypedExpr( new NameExpr( "?*?" ) );
597 multiply->get_args().push_back( appExpr->get_args().back() );
598 multiply->get_args().push_back( new NameExpr( typeInst1->get_name() ) );
599 ret->get_args().push_back( appExpr->get_args().front() );
600 ret->get_args().push_back( multiply );
601 } else if ( typeInst2 ) {
602 UntypedExpr *multiply = new UntypedExpr( new NameExpr( "?*?" ) );
603 multiply->get_args().push_back( appExpr->get_args().front() );
604 multiply->get_args().push_back( new NameExpr( typeInst2->get_name() ) );
605 ret->get_args().push_back( multiply );
606 ret->get_args().push_back( appExpr->get_args().back() );
607 } // if
608 if ( typeInst1 || typeInst2 ) {
609 ret->get_results().push_front( appExpr->get_results().front()->clone() );
610 if ( appExpr->get_env() ) {
611 ret->set_env( appExpr->get_env() );
612 appExpr->set_env( 0 );
613 } // if
614 appExpr->get_args().clear();
615 delete appExpr;
616 return ret;
617 } // if
618 } else if ( varExpr->get_var()->get_name() == "*?" ) {
619 assert( !appExpr->get_results().empty() );
620 assert( !appExpr->get_args().empty() );
621 if ( isPolyType( appExpr->get_results().front(), env, scopeTyVars ) ) {
622 Expression *ret = appExpr->get_args().front();
623 delete ret->get_results().front();
624 ret->get_results().front() = appExpr->get_results().front()->clone();
625 if ( appExpr->get_env() ) {
626 ret->set_env( appExpr->get_env() );
627 appExpr->set_env( 0 );
628 } // if
629 appExpr->get_args().clear();
630 delete appExpr;
631 return ret;
632 } // if
633 } else if ( varExpr->get_var()->get_name() == "?++" || varExpr->get_var()->get_name() == "?--" ) {
634 assert( !appExpr->get_results().empty() );
635 assert( appExpr->get_args().size() == 1 );
636 if ( TypeInstType *typeInst = isPolyPtr( appExpr->get_results().front(), env, scopeTyVars ) ) {
637 Type *tempType = appExpr->get_results().front()->clone();
638 if ( env ) {
639 env->apply( tempType );
640 } // if
641 ObjectDecl *newObj = makeTemporary( tempType );
642 VariableExpr *tempExpr = new VariableExpr( newObj );
643 UntypedExpr *assignExpr = new UntypedExpr( new NameExpr( "?=?" ) );
644 assignExpr->get_args().push_back( tempExpr->clone() );
645 if ( AddressExpr *address = dynamic_cast< AddressExpr *>( appExpr->get_args().front() ) ) {
646 assignExpr->get_args().push_back( address->get_arg()->clone() );
647 } else {
648 assignExpr->get_args().push_back( appExpr->get_args().front()->clone() );
649 } // if
650 CommaExpr *firstComma = new CommaExpr( assignExpr, makeIncrDecrExpr( appExpr, typeInst->get_name(), varExpr->get_var()->get_name() == "?++" ) );
651 return new CommaExpr( firstComma, tempExpr );
652 } // if
653 } else if ( varExpr->get_var()->get_name() == "++?" || varExpr->get_var()->get_name() == "--?" ) {
654 assert( !appExpr->get_results().empty() );
655 assert( appExpr->get_args().size() == 1 );
656 if ( TypeInstType *typeInst = isPolyPtr( appExpr->get_results().front(), env, scopeTyVars ) ) {
657 return makeIncrDecrExpr( appExpr, typeInst->get_name(), varExpr->get_var()->get_name() == "++?" );
658 } // if
659 } else if ( varExpr->get_var()->get_name() == "?+?" || varExpr->get_var()->get_name() == "?-?" ) {
660 assert( !appExpr->get_results().empty() );
661 assert( appExpr->get_args().size() == 2 );
662 TypeInstType *typeInst1 = isPolyPtr( appExpr->get_args().front()->get_results().front(), env, scopeTyVars );
663 TypeInstType *typeInst2 = isPolyPtr( appExpr->get_args().back()->get_results().front(), env, scopeTyVars );
664 if ( typeInst1 && typeInst2 ) {
665 UntypedExpr *divide = new UntypedExpr( new NameExpr( "?/?" ) );
666 divide->get_args().push_back( appExpr );
667 divide->get_args().push_back( new NameExpr( typeInst1->get_name() ) );
668 divide->get_results().push_front( appExpr->get_results().front()->clone() );
669 if ( appExpr->get_env() ) {
670 divide->set_env( appExpr->get_env() );
671 appExpr->set_env( 0 );
672 } // if
673 return divide;
674 } else if ( typeInst1 ) {
675 UntypedExpr *multiply = new UntypedExpr( new NameExpr( "?*?" ) );
676 multiply->get_args().push_back( appExpr->get_args().back() );
677 multiply->get_args().push_back( new NameExpr( typeInst1->get_name() ) );
678 appExpr->get_args().back() = multiply;
679 } else if ( typeInst2 ) {
680 UntypedExpr *multiply = new UntypedExpr( new NameExpr( "?*?" ) );
681 multiply->get_args().push_back( appExpr->get_args().front() );
682 multiply->get_args().push_back( new NameExpr( typeInst2->get_name() ) );
683 appExpr->get_args().front() = multiply;
684 } // if
685 } else if ( varExpr->get_var()->get_name() == "?+=?" || varExpr->get_var()->get_name() == "?-=?" ) {
686 assert( !appExpr->get_results().empty() );
687 assert( appExpr->get_args().size() == 2 );
688 TypeInstType *typeInst = isPolyPtr( appExpr->get_results().front(), env, scopeTyVars );
689 if ( typeInst ) {
690 UntypedExpr *multiply = new UntypedExpr( new NameExpr( "?*?" ) );
691 multiply->get_args().push_back( appExpr->get_args().back() );
692 multiply->get_args().push_back( new NameExpr( typeInst->get_name() ) );
693 appExpr->get_args().back() = multiply;
694 } // if
695 } // if
696 return appExpr;
697 } // if
698 } // if
699 return 0;
700 }
701
702 Expression *Pass1::mutate( ApplicationExpr *appExpr ) {
703/// std::cerr << "mutate appExpr: ";
704/// for ( TyVarMap::iterator i = scopeTyVars.begin(); i != scopeTyVars.end(); ++i ) {
705/// std::cerr << i->first << " ";
706/// }
707/// std::cerr << "\n";
708 bool oldUseRetval = useRetval;
709 useRetval = false;
710 appExpr->get_function()->acceptMutator( *this );
711 mutateAll( appExpr->get_args(), *this );
712 useRetval = oldUseRetval;
713
714 assert( !appExpr->get_function()->get_results().empty() );
715 PointerType *pointer = dynamic_cast< PointerType *>( appExpr->get_function()->get_results().front() );
716 assert( pointer );
717 FunctionType *function = dynamic_cast< FunctionType *>( pointer->get_base() );
718 assert( function );
719
720 if ( Expression *newExpr = handleIntrinsics( appExpr ) ) {
721 return newExpr;
722 } // if
723
724 Expression *ret = appExpr;
725
726 std::list< Expression *>::iterator arg = appExpr->get_args().begin();
727 std::list< Expression *>::iterator paramBegin = appExpr->get_args().begin();
728
729 std::string typeName;
730 if ( isPolyRet( function, typeName ) ) {
731 ret = addPolyRetParam( appExpr, function, typeName, arg );
732 } else if ( needsAdapter( function, scopeTyVars ) ) {
733/// std::cerr << "needs adapter: ";
734/// for ( TyVarMap::iterator i = scopeTyVars.begin(); i != scopeTyVars.end(); ++i ) {
735/// std::cerr << i->first << " ";
736/// }
737/// std::cerr << "\n";
738 // change the application so it calls the adapter rather than the passed function
739 ret = applyAdapter( appExpr, function, arg, scopeTyVars );
740 } // if
741 arg = appExpr->get_args().begin();
742
743 TyVarMap exprTyVars;
744 makeTyVarMap( function, exprTyVars );
745
746 passTypeVars( appExpr, arg, exprTyVars );
747 addInferredParams( appExpr, function, arg, exprTyVars );
748
749 arg = paramBegin;
750
751 boxParams( appExpr, function, arg, exprTyVars );
752
753 passAdapters( appExpr, function, exprTyVars );
754
755 return ret;
756 }
757
758 Expression *Pass1::mutate( UntypedExpr *expr ) {
759 if ( !expr->get_results().empty() && isPolyType( expr->get_results().front(), env, scopeTyVars ) ) {
760 if ( NameExpr *name = dynamic_cast< NameExpr *>( expr->get_function() ) ) {
761 if ( name->get_name() == "*?" ) {
762 Expression *ret = expr->get_args().front();
763 expr->get_args().clear();
764 delete expr;
765 return ret->acceptMutator( *this );
766 } // if
767 } // if
768 } // if
769 return PolyMutator::mutate( expr );
770 }
771
772 Expression *Pass1::mutate( AddressExpr *addrExpr ) {
773 assert( !addrExpr->get_arg()->get_results().empty() );
774 mutateExpression( addrExpr->get_arg() );
775 if ( isPolyType( addrExpr->get_arg()->get_results().front(), env, scopeTyVars ) ) {
776 Expression *ret = addrExpr->get_arg();
777 delete ret->get_results().front();
778 ret->get_results().front() = addrExpr->get_results().front()->clone();
779 addrExpr->set_arg( 0 );
780 delete addrExpr;
781 return ret;
782 } else {
783 return addrExpr;
784 } // if
785 }
786
787 Statement *
788 Pass1::mutate(ReturnStmt *retStmt) {
789 // a cast expr on a polymorphic return value is either redundant or invalid
790 while ( CastExpr *castExpr = dynamic_cast< CastExpr *>( retStmt->get_expr() ) ) {
791 retStmt->set_expr( castExpr->get_arg() );
792 retStmt->get_expr()->set_env( castExpr->get_env() );
793 castExpr->set_env( 0 );
794 castExpr->set_arg( 0 );
795 delete castExpr;
796 }
797 if ( retval && retStmt->get_expr() ) {
798 assert( !retStmt->get_expr()->get_results().empty() );
799 if ( retStmt->get_expr()->get_results().front()->get_isLvalue() ) {
800/// retStmt->set_expr( mutateExpression( retStmt->get_expr() ) );
801 TypeInstType *typeInst = dynamic_cast< TypeInstType *>( retval->get_type() );
802 assert( typeInst );
803 std::map< std::string, DeclarationWithType *>::const_iterator assignIter = assignOps.find( typeInst->get_name() );
804 if ( assignIter == assignOps.end() ) {
805 throw SemanticError( "Attempt to return dtype or ftype object in ", retStmt->get_expr() );
806 } // if
807 ApplicationExpr *assignExpr = new ApplicationExpr( new VariableExpr( assignIter->second ) );
808 Expression *retParm = new NameExpr( retval->get_name() );
809 retParm->get_results().push_back( new PointerType( Type::Qualifiers(), retval->get_type()->clone() ) );
810 assignExpr->get_args().push_back( retParm );
811 assignExpr->get_args().push_back( retStmt->get_expr() );
812 stmtsToAdd.push_back( new ExprStmt( noLabels, mutateExpression( assignExpr ) ) );
813 } else {
814 useRetval = true;
815 stmtsToAdd.push_back( new ExprStmt( noLabels, mutateExpression( retStmt->get_expr() ) ) );
816 useRetval = false;
817 } // if
818 retStmt->set_expr( 0 );
819 } else {
820 retStmt->set_expr( mutateExpression( retStmt->get_expr() ) );
821 } // if
822 return retStmt;
823 }
824
825 Type *
826 Pass1::mutate( PointerType *pointerType ) {
827 TyVarMap oldtyVars = scopeTyVars;
828 makeTyVarMap( pointerType, scopeTyVars );
829
830 Type *ret = Mutator::mutate( pointerType );
831
832 scopeTyVars = oldtyVars;
833 return ret;
834 }
835
836 Type *
837 Pass1::mutate( FunctionType *functionType ) {
838 TyVarMap oldtyVars = scopeTyVars;
839 makeTyVarMap( functionType, scopeTyVars );
840
841 Type *ret = Mutator::mutate( functionType );
842
843 scopeTyVars = oldtyVars;
844 return ret;
845 }
846
847 void Pass1::doEndScope() {
848 adapters.clear();
849 }
850
851////////////////////////////////////////// Pass2 ////////////////////////////////////////////////////
852
853 Pass2::Pass2() {}
854
855 void Pass2::addAdapters( FunctionType *functionType ) {
856 std::list< DeclarationWithType *> &paramList = functionType->get_parameters();
857 std::list< FunctionType *> functions;
858 for ( std::list< DeclarationWithType *>::iterator arg = paramList.begin(); arg != paramList.end(); ++arg ) {
859 Type *orig = (*arg)->get_type();
860 findAndReplaceFunction( orig, functions, scopeTyVars, needsAdapter );
861 (*arg)->set_type( orig );
862 }
863 std::set< std::string > adaptersDone;
864 for ( std::list< FunctionType *>::iterator funType = functions.begin(); funType != functions.end(); ++funType ) {
865 std::string mangleName = SymTab::Mangler::mangle( *funType );
866 if ( adaptersDone.find( mangleName ) == adaptersDone.end() ) {
867 paramList.push_front( new ObjectDecl( "_adapter" + mangleName, Declaration::NoStorageClass, LinkageSpec::C, 0, new PointerType( Type::Qualifiers(), makeAdapterType( *funType, scopeTyVars ) ), 0 ) );
868 adaptersDone.insert( adaptersDone.begin(), mangleName );
869 }
870 }
871/// deleteAll( functions );
872 }
873
874 template< typename DeclClass >
875 DeclClass *
876 Pass2::handleDecl( DeclClass *decl, Type *type ) {
877 DeclClass *ret = static_cast< DeclClass *>( Mutator::mutate( decl ) );
878
879 return ret;
880 }
881
882 DeclarationWithType *
883 Pass2::mutate( FunctionDecl *functionDecl ) {
884 return handleDecl( functionDecl, functionDecl->get_functionType() );
885 }
886
887 ObjectDecl *
888 Pass2::mutate( ObjectDecl *objectDecl ) {
889 return handleDecl( objectDecl, objectDecl->get_type() );
890 }
891
892 TypeDecl *
893 Pass2::mutate( TypeDecl *typeDecl ) {
894 scopeTyVars[ typeDecl->get_name() ] = typeDecl->get_kind();
895 if ( typeDecl->get_base() ) {
896 return handleDecl( typeDecl, typeDecl->get_base() );
897 } else {
898 return Mutator::mutate( typeDecl );
899 }
900 }
901
902 TypedefDecl *
903 Pass2::mutate( TypedefDecl *typedefDecl ) {
904 return handleDecl( typedefDecl, typedefDecl->get_base() );
905 }
906
907 Type *
908 Pass2::mutate( PointerType *pointerType ) {
909 TyVarMap oldtyVars = scopeTyVars;
910 makeTyVarMap( pointerType, scopeTyVars );
911
912 Type *ret = Mutator::mutate( pointerType );
913
914 scopeTyVars = oldtyVars;
915 return ret;
916 }
917
918 Type *Pass2::mutate( FunctionType *funcType ) {
919 TyVarMap oldtyVars = scopeTyVars;
920 makeTyVarMap( funcType, scopeTyVars );
921
922 std::string typeName;
923 if ( isPolyRet( funcType, typeName ) ) {
924 DeclarationWithType *ret = funcType->get_returnVals().front();
925 ret->set_type( new PointerType( Type::Qualifiers(), ret->get_type() ) );
926 funcType->get_parameters().push_front( ret );
927 funcType->get_returnVals().pop_front();
928 }
929
930 std::list< DeclarationWithType *>::iterator last = funcType->get_parameters().begin();
931 std::list< DeclarationWithType *> inferredParams;
932 ObjectDecl *newObj = new ObjectDecl( "", Declaration::NoStorageClass, LinkageSpec::C, 0, new BasicType( Type::Qualifiers(), BasicType::LongUnsignedInt ), 0 );
933/// ObjectDecl *newFunPtr = new ObjectDecl( "", Declaration::NoStorageClass, LinkageSpec::Cforall, 0, new PointerType( Type::Qualifiers(), new FunctionType( Type::Qualifiers(), true ) ), 0 );
934 for ( std::list< TypeDecl *>::const_iterator tyParm = funcType->get_forall().begin(); tyParm != funcType->get_forall().end(); ++tyParm ) {
935 ObjectDecl *thisParm;
936 if ( (*tyParm)->get_kind() == TypeDecl::Any ) {
937 thisParm = newObj->clone();
938 thisParm->set_name( (*tyParm)->get_name() );
939 last = funcType->get_parameters().insert( last, thisParm );
940 ++last;
941 }
942 for ( std::list< DeclarationWithType *>::iterator assert = (*tyParm)->get_assertions().begin(); assert != (*tyParm)->get_assertions().end(); ++assert ) {
943/// *assert = (*assert)->acceptMutator( *this );
944 inferredParams.push_back( *assert );
945 }
946 (*tyParm)->get_assertions().clear();
947 }
948 delete newObj;
949 funcType->get_parameters().splice( last, inferredParams );
950 addAdapters( funcType );
951 mutateAll( funcType->get_returnVals(), *this );
952 mutateAll( funcType->get_parameters(), *this );
953
954 scopeTyVars = oldtyVars;
955 return funcType;
956 }
957
958////////////////////////////////////////// Pass3 ////////////////////////////////////////////////////
959
960 template< typename DeclClass >
961 DeclClass *
962 Pass3::handleDecl( DeclClass *decl, Type *type ) {
963 TyVarMap oldtyVars = scopeTyVars;
964 makeTyVarMap( type, scopeTyVars );
965
966 DeclClass *ret = static_cast< DeclClass *>( Mutator::mutate( decl ) );
967 ScrubTyVars::scrub( decl, scopeTyVars );
968
969 scopeTyVars = oldtyVars;
970 return ret;
971 }
972
973 ObjectDecl *
974 Pass3::mutate( ObjectDecl *objectDecl ) {
975 return handleDecl( objectDecl, objectDecl->get_type() );
976 }
977
978 DeclarationWithType *
979 Pass3::mutate( FunctionDecl *functionDecl ) {
980 return handleDecl( functionDecl, functionDecl->get_functionType() );
981 }
982
983 TypedefDecl *
984 Pass3::mutate( TypedefDecl *typedefDecl ) {
985 return handleDecl( typedefDecl, typedefDecl->get_base() );
986 }
987
988 TypeDecl *
989 Pass3::mutate( TypeDecl *typeDecl ) {
990/// Initializer *init = 0;
991/// std::list< Expression *> designators;
992/// scopeTyVars[ typeDecl->get_name() ] = typeDecl->get_kind();
993/// if ( typeDecl->get_base() ) {
994/// init = new SimpleInit( new SizeofExpr( handleDecl( typeDecl, typeDecl->get_base() ) ), designators );
995/// }
996/// return new ObjectDecl( typeDecl->get_name(), Declaration::Extern, LinkageSpec::C, 0, new BasicType( Type::Qualifiers(), BasicType::UnsignedInt ), init );
997
998 scopeTyVars[ typeDecl->get_name() ] = typeDecl->get_kind();
999 return Mutator::mutate( typeDecl );
1000 }
1001
1002 Type *
1003 Pass3::mutate( PointerType *pointerType ) {
1004 TyVarMap oldtyVars = scopeTyVars;
1005 makeTyVarMap( pointerType, scopeTyVars );
1006
1007 Type *ret = Mutator::mutate( pointerType );
1008
1009 scopeTyVars = oldtyVars;
1010 return ret;
1011 }
1012
1013 Type *
1014 Pass3::mutate( FunctionType *functionType ) {
1015 TyVarMap oldtyVars = scopeTyVars;
1016 makeTyVarMap( functionType, scopeTyVars );
1017
1018 Type *ret = Mutator::mutate( functionType );
1019
1020 scopeTyVars = oldtyVars;
1021 return ret;
1022 }
1023
1024 Statement *Pass3::mutate( DeclStmt *declStmt ) {
1025 if ( ObjectDecl *objectDecl = dynamic_cast< ObjectDecl *>( declStmt->get_decl() ) ) {
1026 if ( isPolyVal( objectDecl->get_type(), scopeTyVars ) ) {
1027 TypeInstType *typeInst = dynamic_cast< TypeInstType *>( objectDecl->get_type() );
1028 assert( typeInst );
1029 UntypedExpr *alloc = new UntypedExpr( new NameExpr( "alloca" ) );
1030 alloc->get_args().push_back( new NameExpr( typeInst->get_name() ) );
1031 UntypedExpr *assign = new UntypedExpr( new NameExpr( "?=?" ) );
1032 assign->get_args().push_back( new VariableExpr( objectDecl ) );
1033 assign->get_args().push_back( alloc );
1034 stmtsToAddAfter.push_back( new ExprStmt( noLabels, assign ) );
1035 }
1036 }
1037 return Mutator::mutate( declStmt );
1038 }
1039
1040 } // anonymous namespace
1041
1042} // namespace GenPoly
Note: See TracBrowser for help on using the repository browser.