InstLamHoist.cxx

Go to the documentation of this file.
00001 /**************************************************************************
00002  *
00003  * Copyright (C) 2008, Johns Hopkins University.
00004  * All rights reserved.
00005  *
00006  * Redistribution and use in source and binary forms, with or
00007  * without modification, are permitted provided that the following
00008  * conditions are met:
00009  *
00010  *   - Redistributions of source code must contain the above
00011  *     copyright notice, this list of conditions, and the following
00012  *     disclaimer.
00013  *
00014  *   - Redistributions in binary form must reproduce the above
00015  *     copyright notice, this list of conditions, and the following
00016  *     disclaimer in the documentation and/or other materials
00017  *     provided with the distribution.
00018  *
00019  *   - Neither the names of the copyright holders nor the names of any
00020  *     of any contributors may be used to endorse or promote products
00021  *     derived from this software without specific prior written
00022  *     permission.
00023  *
00024  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
00025  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
00026  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
00027  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
00028  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
00029  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
00030  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
00031  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
00032  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
00033  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
00034  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00035  *
00036  **************************************************************************/
00037 
00038 /* In order to successfully polyinstantiate instances that contain
00039    immediate lambdas, we need to hoist them and give them proper
00040    names so that the polyinstantiator has something to mangle. */
00041 
00042 #include <assert.h>
00043 #include <stdint.h>
00044 #include <stdlib.h>
00045 #include <dirent.h>
00046 #include <fstream>
00047 #include <iostream>
00048 #include <sstream>
00049 #include <string>
00050 
00051 #include <libsherpa/UExcept.hxx>
00052 
00053 #include "UocInfo.hxx"
00054 #include "AST.hxx"
00055 #include "Type.hxx"
00056 #include "TypeInfer.hxx"
00057 #include "inter-pass.hxx"
00058 
00059 using namespace boost;
00060 using namespace sherpa;
00061 
00062 static void
00063 cl_HoistInstLam(shared_ptr<UocInfo> uoc)
00064 {
00065   std::vector<shared_ptr<AST> > outAsts;
00066 
00067   shared_ptr<AST> modOrIf = uoc->uocAst;
00068 
00069   for (size_t c = 0;c < modOrIf->children.size(); c++) {
00070     shared_ptr<AST> child = modOrIf->child(c);
00071 
00072     if (child->astType == at_definstance) {
00073       shared_ptr<AST> methods = child->child(1);
00074 
00075       // FIX: This is **utterly failing** to hoist the constraints, so
00076       // any constraint that is not on an instantiated variable will
00077       // not do the right thing.
00078       for (size_t m = 0; m < methods->children.size(); m++) {
00079         shared_ptr<AST> method = methods->child(m);
00080         shared_ptr<AST> methodValue = method->child(1);
00081         
00082         if (methodValue->astType != at_ident) {
00083           // It's an expression. Since instance definitions consist
00084           // entirely of procedure bindings/mappings, and we know this
00085           // type checked, it must be a lambda. Need to hoist it into
00086           // a top-level binding and replace the expression occurrence
00087           // with the resulting identifier.
00088           shared_ptr<AST> newDef = AST::make(at_define, methodValue->loc);
00089 
00090           shared_ptr<AST> lamName = AST::genSym(methodValue, "lam");
00091           lamName->identType = id_value;
00092           lamName->flags |= ID_IS_GLOBAL;
00093 
00094           shared_ptr<AST> lamPat = AST::make(at_identPattern,
00095                                              methodValue->loc, lamName); 
00096           newDef->addChild(lamPat);
00097           newDef->addChild(methodValue);
00098           newDef->addChild(AST::make(at_constraints));
00099 
00100           outAsts.push_back(newDef);
00101 
00102           shared_ptr<AST> instName = lamName->Use();
00103           shared_ptr<AST> the = AST::make(at_typeAnnotation);
00104           the->addChild(instName);
00105           the->addChild(methodValue->symType->asAST(methodValue->loc));
00106 
00107           method->child(1) = the;
00108         }
00109       }
00110     }
00111 
00112     outAsts.push_back(child);
00113   }
00114 
00115   modOrIf->children = outAsts;
00116 }
00117 
00118 #if 0
00119 bool
00120 UocInfo::be_HoistInstLam(std::ostream& errStream,
00121                          bool init, unsigned long flags)
00122 {
00123   bool errFree = true;
00124 
00125   shared_ptr<AST> &ast = UocInfo::linkedUoc.ast;
00126 
00127   DEBUG(ILH) if (isSourceUoc)
00128     BitcPP(errStream, &UocInfo::linkedUoc);
00129 
00130   DEBUG(ILH) std::cerr << "cl_HoistInstLam" << std::endl;
00131   cl_HoistInstLam(&UocInfo::linkedUoc);
00132 
00133   DEBUG(ILH) if (isSourceUoc)
00134     BitcPP(errStream, &UocInfo::linkedUoc);
00135 
00136   DEBUG(ILH) std::cerr << "RandT" << std::endl;
00137   // Re-run the type checker to propagate the changes:
00138   CHKERR(errFree, RandT(errStream, &UocInfo::linkedUoc, true, POLY_SYM_FLAGS, POLY_TYP_FLAGS));
00139   assert(errFree);
00140 
00141   return true;
00142 }
00143 #else
00144 bool
00145 UocInfo::fe_HoistInstLam(std::ostream& errStream,
00146                          bool init, unsigned long flags)
00147 {
00148   bool errFree = true;
00149 
00150   DEBUG(ILH) if (isSourceUoc())
00151     PrettyPrint(errStream);
00152 
00153   DEBUG(ILH) std::cerr << "cl_HoistInstLam" << std::endl;
00154   cl_HoistInstLam(shared_from_this());
00155   
00156   DEBUG(ILH) if (isSourceUoc())
00157     PrettyPrint(errStream);
00158   
00159   DEBUG(ILH) std::cerr << "RandT" << std::endl;
00160   // Re-run the type checker to propagate the changes:
00161   CHKERR(errFree, RandT(errStream, true, PI_SYM_FLAGS, PI_TYP_FLAGS));
00162   assert(errFree);
00163 
00164   return true;
00165 }
00166 #endif

Generated on Fri Feb 10 07:59:20 2012 for BitC Compiler by  doxygen 1.4.7