This machine mirrors various open-source projects.
20 Gbit/s uplink.
If there are any issues or you want another project mirrored, please contact
mirror-service -=AT=- netcologne DOT de !
00001 //===-- ast/AstRewriter.cpp ----------------------------------- -*- C++ -*-===// 00002 // 00003 // This file is distributed under the MIT license. See LICENSE.txt for details. 00004 // 00005 // Copyright (C) 2008-2010, Stephen Wilson 00006 // 00007 //===----------------------------------------------------------------------===// 00008 00009 #include "comma/ast/AstResource.h" 00010 #include "comma/ast/AstRewriter.h" 00011 #include "comma/ast/Decl.h" 00012 #include "comma/ast/Type.h" 00013 00014 #include "llvm/Support/Casting.h" 00015 #include "llvm/ADT/SmallVector.h" 00016 00017 using namespace comma; 00018 using llvm::dyn_cast; 00019 using llvm::dyn_cast_or_null; 00020 using llvm::cast; 00021 using llvm::isa; 00022 00023 Type *AstRewriter::findRewrite(Type *source) const 00024 { 00025 RewriteMap::const_iterator iter = rewrites.find(source); 00026 if (iter == rewrites.end()) 00027 return 0; 00028 return iter->second; 00029 } 00030 00031 Type *AstRewriter::getRewrite(Type *source) const 00032 { 00033 if (Type *res = findRewrite(source)) 00034 return res; 00035 return source; 00036 } 00037 00038 void AstRewriter::installRewrites(DomainType *context) 00039 { 00040 // If this type is parameterized, install rewites mapping the formal 00041 // arguments of the underlying functor to the actual arguments of the type. 00042 if (DomainInstanceDecl *instance = context->getInstanceDecl()) { 00043 if (FunctorDecl *functor = instance->getDefiningFunctor()) { 00044 unsigned arity = instance->getArity(); 00045 for (unsigned i = 0; i < arity; ++i) { 00046 DomainType *formal = functor->getFormalType(i); 00047 Type *actual = instance->getActualParamType(i); 00048 rewrites[formal] = actual; 00049 } 00050 } 00051 } 00052 } 00053 00054 void AstRewriter::installRewrites(SigInstanceDecl *context) 00055 { 00056 VarietyDecl *variety = context->getVariety(); 00057 00058 if (variety) { 00059 unsigned arity = variety->getArity(); 00060 for (unsigned i = 0; i < arity; ++i) { 00061 DomainType *formal = variety->getFormalType(i); 00062 Type *actual = context->getActualParamType(i); 00063 addTypeRewrite(formal, actual); 00064 } 00065 } 00066 } 00067 00068 Type *AstRewriter::rewriteType(Type *type) const 00069 { 00070 if (Type *result = findRewrite(type)) 00071 return result; 00072 00073 switch(type->getKind()) { 00074 00075 default: return type; 00076 00077 case Ast::AST_DomainType: 00078 return rewriteType(cast<DomainType>(type)); 00079 case Ast::AST_FunctionType: 00080 return rewriteType(cast<FunctionType>(type)); 00081 case Ast::AST_ProcedureType: 00082 return rewriteType(cast<ProcedureType>(type)); 00083 } 00084 } 00085 00086 SigInstanceDecl *AstRewriter::rewriteSigInstance(SigInstanceDecl *sig) const 00087 { 00088 if (sig->isParameterized()) { 00089 llvm::SmallVector<DomainTypeDecl*, 4> args; 00090 SigInstanceDecl::arg_iterator iter; 00091 SigInstanceDecl::arg_iterator endIter = sig->endArguments(); 00092 for (iter = sig->beginArguments(); iter != endIter; ++iter) { 00093 // FIXME: Currently it is true that all arguments are domains, but 00094 // in the future we will need to be more general than this. 00095 DomainType *argTy = rewriteType((*iter)->getType()); 00096 args.push_back(argTy->getDomainTypeDecl()); 00097 } 00098 // Obtain a memoized instance. 00099 VarietyDecl *decl = sig->getVariety(); 00100 return decl->getInstance(&args[0], args.size()); 00101 } 00102 return sig; 00103 } 00104 00105 DomainType *AstRewriter::rewriteType(DomainType *dom) const 00106 { 00107 if (DomainType *result = dyn_cast_or_null<DomainType>(findRewrite(dom))) 00108 return result; 00109 00110 if (DomainInstanceDecl *instance = dom->getInstanceDecl()) { 00111 if (FunctorDecl *functor = instance->getDefiningFunctor()) { 00112 typedef DomainInstanceDecl::arg_iterator iterator; 00113 llvm::SmallVector<DomainTypeDecl*, 4> args; 00114 iterator iter; 00115 iterator endIter = instance->endArguments(); 00116 for (iter = instance->beginArguments(); iter != endIter; ++iter) { 00117 // FIXME: Currently it is true that all arguments are domains, 00118 // but in the future we will need to be more general than this. 00119 DomainType *argTy = rewriteType((*iter)->getType()); 00120 args.push_back(argTy->getDomainTypeDecl()); 00121 } 00122 // Obtain a memoized instance and return the associated type. 00123 instance = functor->getInstance(&args[0], args.size()); 00124 return instance->getType(); 00125 } 00126 } 00127 return dom; 00128 } 00129 00130 SubroutineType *AstRewriter::rewriteType(SubroutineType *srType) const 00131 { 00132 if (ProcedureType *ptype = dyn_cast<ProcedureType>(srType)) 00133 return rewriteType(ptype); 00134 00135 return rewriteType(cast<FunctionType>(srType)); 00136 } 00137 00138 void AstRewriter::rewriteParameters(SubroutineType *srType, 00139 unsigned count, Type **params) const 00140 { 00141 for (unsigned i = 0; i < count; ++i) 00142 params[i] = getRewrite(srType->getArgType(i)); 00143 } 00144 00145 FunctionType *AstRewriter::rewriteType(FunctionType *ftype) const 00146 { 00147 unsigned arity = ftype->getArity(); 00148 Type *returnType = getRewrite(ftype->getReturnType()); 00149 Type *paramTypes[arity]; 00150 00151 rewriteParameters(ftype, arity, paramTypes); 00152 return resource.getFunctionType(paramTypes, arity, returnType); 00153 } 00154 00155 ProcedureType *AstRewriter::rewriteType(ProcedureType *ptype) const 00156 { 00157 unsigned arity = ptype->getArity(); 00158 Type *paramTypes[arity]; 00159 00160 rewriteParameters(ptype, arity, paramTypes); 00161 return resource.getProcedureType(paramTypes, arity); 00162 }