Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/SymTab/Mangler.cc

    r4071778 r3530f39a  
    1010// Created On       : Sun May 17 21:40:29 2015
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Tue Jul 30 13:46:10 2019
    13 // Update Count     : 26
     12// Last Modified On : Mon Sep 25 15:49:26 2017
     13// Update Count     : 23
    1414//
    1515#include "Mangler.h"
    1616
    17 #include <algorithm>                     // for copy, transform
    18 #include <cassert>                       // for assert, assertf
    19 #include <functional>                    // for const_mem_fun_t, mem_fun
    20 #include <iterator>                      // for ostream_iterator, back_insert_ite...
    21 #include <list>                          // for _List_iterator, list, _List_const...
    22 #include <string>                        // for string, char_traits, operator<<
    23 
    24 #include "CodeGen/OperatorTable.h"       // for OperatorInfo, operatorLookup
     17#include <algorithm>                // for copy, transform
     18#include <cassert>                  // for assert, assertf
     19#include <functional>               // for const_mem_fun_t, mem_fun
     20#include <iterator>                 // for ostream_iterator, back_insert_ite...
     21#include <list>                     // for _List_iterator, list, _List_const...
     22#include <string>                   // for string, char_traits, operator<<
     23
     24#include "CodeGen/OperatorTable.h"  // for OperatorInfo, operatorLookup
    2525#include "Common/PassVisitor.h"
    26 #include "Common/SemanticError.h"        // for SemanticError
    27 #include "Common/utility.h"              // for toString
    28 #include "Parser/LinkageSpec.h"          // for Spec, isOverridable, AutoGen, Int...
    29 #include "ResolvExpr/TypeEnvironment.h"  // for TypeEnvironment
    30 #include "SynTree/Declaration.h"         // for TypeDecl, DeclarationWithType
    31 #include "SynTree/Expression.h"          // for TypeExpr, Expression, operator<<
    32 #include "SynTree/Type.h"                // for Type, ReferenceToType, Type::Fora...
    33 
    34 #include "AST/Pass.hpp"
     26#include "Common/SemanticError.h"   // for SemanticError
     27#include "Common/utility.h"         // for toString
     28#include "Parser/LinkageSpec.h"     // for Spec, isOverridable, AutoGen, Int...
     29#include "SynTree/Declaration.h"    // for TypeDecl, DeclarationWithType
     30#include "SynTree/Expression.h"     // for TypeExpr, Expression, operator<<
     31#include "SynTree/Type.h"           // for Type, ReferenceToType, Type::Fora...
    3532
    3633namespace SymTab {
     
    3835                namespace {
    3936                        /// Mangles names to a unique C identifier
    40                         struct Mangler_old : public WithShortCircuiting, public WithVisitorRef<Mangler_old>, public WithGuards {
    41                                 Mangler_old( bool mangleOverridable, bool typeMode, bool mangleGenericParams );
    42                                 Mangler_old( const Mangler_old & ) = delete;
    43 
    44                                 void previsit( const BaseSyntaxNode * ) { visit_children = false; }
    45 
    46                                 void postvisit( const ObjectDecl * declaration );
    47                                 void postvisit( const FunctionDecl * declaration );
    48                                 void postvisit( const TypeDecl * declaration );
    49 
    50                                 void postvisit( const VoidType * voidType );
    51                                 void postvisit( const BasicType * basicType );
    52                                 void postvisit( const PointerType * pointerType );
    53                                 void postvisit( const ArrayType * arrayType );
    54                                 void postvisit( const ReferenceType * refType );
    55                                 void postvisit( const FunctionType * functionType );
    56                                 void postvisit( const StructInstType * aggregateUseType );
    57                                 void postvisit( const UnionInstType * aggregateUseType );
    58                                 void postvisit( const EnumInstType * aggregateUseType );
    59                                 void postvisit( const TypeInstType * aggregateUseType );
    60                                 void postvisit( const TraitInstType * inst );
    61                                 void postvisit( const TupleType * tupleType );
    62                                 void postvisit( const VarArgsType * varArgsType );
    63                                 void postvisit( const ZeroType * zeroType );
    64                                 void postvisit( const OneType * oneType );
    65                                 void postvisit( const QualifiedType * qualType );
     37                        struct Mangler : public WithShortCircuiting, public WithVisitorRef<Mangler>, public WithGuards {
     38                                Mangler( bool mangleOverridable, bool typeMode, bool mangleGenericParams );
     39                                Mangler( const Mangler & ) = delete;
     40
     41                                void previsit( BaseSyntaxNode * ) { visit_children = false; }
     42
     43                                void postvisit( ObjectDecl * declaration );
     44                                void postvisit( FunctionDecl * declaration );
     45                                void postvisit( TypeDecl * declaration );
     46
     47                                void postvisit( VoidType * voidType );
     48                                void postvisit( BasicType * basicType );
     49                                void postvisit( PointerType * pointerType );
     50                                void postvisit( ArrayType * arrayType );
     51                                void postvisit( ReferenceType * refType );
     52                                void postvisit( FunctionType * functionType );
     53                                void postvisit( StructInstType * aggregateUseType );
     54                                void postvisit( UnionInstType * aggregateUseType );
     55                                void postvisit( EnumInstType * aggregateUseType );
     56                                void postvisit( TypeInstType * aggregateUseType );
     57                                void postvisit( TraitInstType * inst );
     58                                void postvisit( TupleType * tupleType );
     59                                void postvisit( VarArgsType * varArgsType );
     60                                void postvisit( ZeroType * zeroType );
     61                                void postvisit( OneType * oneType );
    6662
    6763                                std::string get_mangleName() { return mangleName.str(); }
     
    7672                                bool mangleGenericParams;       ///< Include generic parameters in name mangling if true
    7773                                bool inFunctionType = false;    ///< Include type qualifiers if false.
    78                                 bool inQualifiedType = false;   ///< Add start/end delimiters around qualified type
    79 
    80                           public:
    81                                 Mangler_old( bool mangleOverridable, bool typeMode, bool mangleGenericParams,
    82                                         int nextVarNum, const VarMapType& varNums );
    83 
    84                           private:
    85                                 void mangleDecl( const DeclarationWithType * declaration );
    86                                 void mangleRef( const ReferenceToType * refType, std::string prefix );
    87 
    88                                 void printQualifiers( const Type *type );
    89                         }; // Mangler_old
     74
     75                                void mangleDecl( DeclarationWithType *declaration );
     76                                void mangleRef( ReferenceToType *refType, std::string prefix );
     77
     78                                void printQualifiers( Type *type );
     79                        }; // Mangler
    9080                } // namespace
    9181
    92                 std::string mangle( const BaseSyntaxNode * decl, bool mangleOverridable, bool typeMode, bool mangleGenericParams ) {
    93                         PassVisitor<Mangler_old> mangler( mangleOverridable, typeMode, mangleGenericParams );
     82                std::string mangle( BaseSyntaxNode * decl, bool mangleOverridable, bool typeMode, bool mangleGenericParams ) {
     83                        PassVisitor<Mangler> mangler( mangleOverridable, typeMode, mangleGenericParams );
    9484                        maybeAccept( decl, mangler );
    9585                        return mangler.pass.get_mangleName();
    9686                }
    9787
    98                 std::string mangleType( const Type * ty ) {
    99                         PassVisitor<Mangler_old> mangler( false, true, true );
     88                std::string mangleType( Type * ty ) {
     89                        PassVisitor<Mangler> mangler( false, true, true );
    10090                        maybeAccept( ty, mangler );
    10191                        return mangler.pass.get_mangleName();
    10292                }
    10393
    104                 std::string mangleConcrete( const Type * ty ) {
    105                         PassVisitor<Mangler_old> mangler( false, false, false );
     94                std::string mangleConcrete( Type * ty ) {
     95                        PassVisitor<Mangler> mangler( false, false, false );
    10696                        maybeAccept( ty, mangler );
    10797                        return mangler.pass.get_mangleName();
     
    10999
    110100                namespace {
    111                         Mangler_old::Mangler_old( bool mangleOverridable, bool typeMode, bool mangleGenericParams )
    112                                 : nextVarNum( 0 ), isTopLevel( true ),
    113                                 mangleOverridable( mangleOverridable ), typeMode( typeMode ),
    114                                 mangleGenericParams( mangleGenericParams ) {}
    115 
    116                         Mangler_old::Mangler_old( bool mangleOverridable, bool typeMode, bool mangleGenericParams,
    117                                 int nextVarNum, const VarMapType& varNums )
    118                                 : varNums( varNums ), nextVarNum( nextVarNum ), isTopLevel( false ),
    119                                 mangleOverridable( mangleOverridable ), typeMode( typeMode ),
    120                                 mangleGenericParams( mangleGenericParams ) {}
    121 
    122                         void Mangler_old::mangleDecl( const DeclarationWithType * declaration ) {
     101                        Mangler::Mangler( bool mangleOverridable, bool typeMode, bool mangleGenericParams )
     102                                : nextVarNum( 0 ), isTopLevel( true ), mangleOverridable( mangleOverridable ), typeMode( typeMode ), mangleGenericParams( mangleGenericParams ) {}
     103
     104                        void Mangler::mangleDecl( DeclarationWithType * declaration ) {
    123105                                bool wasTopLevel = isTopLevel;
    124106                                if ( isTopLevel ) {
     
    127109                                        isTopLevel = false;
    128110                                } // if
    129                                 mangleName << Encoding::manglePrefix;
     111                                mangleName << "__";
    130112                                CodeGen::OperatorInfo opInfo;
    131113                                if ( operatorLookup( declaration->get_name(), opInfo ) ) {
    132                                         mangleName << opInfo.outputName.size() << opInfo.outputName;
     114                                        mangleName << opInfo.outputName;
    133115                                } else {
    134                                         mangleName << declaration->name.size() << declaration->name;
     116                                        mangleName << declaration->get_name();
    135117                                } // if
     118                                mangleName << "__";
    136119                                maybeAccept( declaration->get_type(), *visitor );
    137120                                if ( mangleOverridable && LinkageSpec::isOverridable( declaration->get_linkage() ) ) {
     
    139122                                        // so they need a different name mangling
    140123                                        if ( declaration->get_linkage() == LinkageSpec::AutoGen ) {
    141                                                 mangleName << Encoding::autogen;
     124                                                mangleName << "autogen__";
    142125                                        } else if ( declaration->get_linkage() == LinkageSpec::Intrinsic ) {
    143                                                 mangleName << Encoding::intrinsic;
     126                                                mangleName << "intrinsic__";
    144127                                        } else {
    145128                                                // if we add another kind of overridable function, this has to change
     
    150133                        }
    151134
    152                         void Mangler_old::postvisit( const ObjectDecl * declaration ) {
     135                        void Mangler::postvisit( ObjectDecl * declaration ) {
    153136                                mangleDecl( declaration );
    154137                        }
    155138
    156                         void Mangler_old::postvisit( const FunctionDecl * declaration ) {
     139                        void Mangler::postvisit( FunctionDecl * declaration ) {
    157140                                mangleDecl( declaration );
    158141                        }
    159142
    160                         void Mangler_old::postvisit( const VoidType * voidType ) {
     143                        void Mangler::postvisit( VoidType * voidType ) {
    161144                                printQualifiers( voidType );
    162                                 mangleName << Encoding::void_t;
    163                         }
    164 
    165                         void Mangler_old::postvisit( const BasicType * basicType ) {
     145                                mangleName << "v";
     146                        }
     147
     148                        void Mangler::postvisit( BasicType * basicType ) {
     149                                static const char *btLetter[] = {
     150                                        "b",    // Bool
     151                                        "c",    // Char
     152                                        "Sc",   // SignedChar
     153                                        "Uc",   // UnsignedChar
     154                                        "s",    // ShortSignedInt
     155                                        "Us",   // ShortUnsignedInt
     156                                        "i",    // SignedInt
     157                                        "Ui",   // UnsignedInt
     158                                        "l",    // LongSignedInt
     159                                        "Ul",   // LongUnsignedInt
     160                                        "q",    // LongLongSignedInt
     161                                        "Uq",   // LongLongUnsignedInt
     162                                        "f",    // Float
     163                                        "d",    // Double
     164                                        "r",    // LongDouble
     165                                        "Xf",   // FloatComplex
     166                                        "Xd",   // DoubleComplex
     167                                        "Xr",   // LongDoubleComplex
     168                                        "If",   // FloatImaginary
     169                                        "Id",   // DoubleImaginary
     170                                        "Ir",   // LongDoubleImaginary
     171                                        "w",    // SignedInt128
     172                                        "Uw",   // UnsignedInt128
     173                                        "x",   // Float80
     174                                        "y",   // Float128
     175                                };
     176                                static_assert(
     177                                        sizeof(btLetter)/sizeof(btLetter[0]) == BasicType::NUMBER_OF_BASIC_TYPES,
     178                                        "Each basic type kind should have a corresponding mangler letter"
     179                                );
     180
    166181                                printQualifiers( basicType );
    167                                 assertf( basicType->kind < BasicType::NUMBER_OF_BASIC_TYPES, "Unhandled basic type: %d", basicType->kind );
    168                                 mangleName << Encoding::basicTypes[ basicType->kind ];
    169                         }
    170 
    171                         void Mangler_old::postvisit( const PointerType * pointerType ) {
     182                                assert( basicType->get_kind() < sizeof(btLetter)/sizeof(btLetter[0]) );
     183                                mangleName << btLetter[ basicType->get_kind() ];
     184                        }
     185
     186                        void Mangler::postvisit( PointerType * pointerType ) {
    172187                                printQualifiers( pointerType );
    173188                                // mangle void (*f)() and void f() to the same name to prevent overloading on functions and function pointers
    174                                 if ( ! dynamic_cast<FunctionType *>( pointerType->base ) ) mangleName << Encoding::pointer;
     189                                if ( ! dynamic_cast<FunctionType *>( pointerType->base ) ) mangleName << "P";
    175190                                maybeAccept( pointerType->base, *visitor );
    176191                        }
    177192
    178                         void Mangler_old::postvisit( const ArrayType * arrayType ) {
     193                        void Mangler::postvisit( ArrayType * arrayType ) {
    179194                                // TODO: encode dimension
    180195                                printQualifiers( arrayType );
    181                                 mangleName << Encoding::array << "0";
     196                                mangleName << "A0";
    182197                                maybeAccept( arrayType->base, *visitor );
    183198                        }
    184199
    185                         void Mangler_old::postvisit( const ReferenceType * refType ) {
     200                        void Mangler::postvisit( ReferenceType * refType ) {
    186201                                // don't print prefix (e.g. 'R') for reference types so that references and non-references do not overload.
    187202                                // Further, do not print the qualifiers for a reference type (but do run printQualifers because of TypeDecls, etc.),
     
    202217                        }
    203218
    204                         void Mangler_old::postvisit( const FunctionType * functionType ) {
     219                        void Mangler::postvisit( FunctionType * functionType ) {
    205220                                printQualifiers( functionType );
    206                                 mangleName << Encoding::function;
     221                                mangleName << "F";
    207222                                // turn on inFunctionType so that printQualifiers does not print most qualifiers for function parameters,
    208223                                // since qualifiers on outermost parameter type do not differentiate function types, e.g.,
     
    211226                                inFunctionType = true;
    212227                                std::list< Type* > returnTypes = getTypes( functionType->returnVals );
    213                                 if (returnTypes.empty()) mangleName << Encoding::void_t;
    214                                 else acceptAll( returnTypes, *visitor );
     228                                acceptAll( returnTypes, *visitor );
    215229                                mangleName << "_";
    216230                                std::list< Type* > paramTypes = getTypes( functionType->parameters );
     
    219233                        }
    220234
    221                         void Mangler_old::mangleRef( const ReferenceToType * refType, std::string prefix ) {
     235                        void Mangler::mangleRef( ReferenceToType * refType, std::string prefix ) {
    222236                                printQualifiers( refType );
    223237
    224                                 mangleName << prefix << refType->name.length() << refType->name;
     238                                mangleName << ( refType->name.length() + prefix.length() ) << prefix << refType->name;
    225239
    226240                                if ( mangleGenericParams ) {
    227                                         const std::list< Expression* > & params = refType->parameters;
     241                                        std::list< Expression* >& params = refType->parameters;
    228242                                        if ( ! params.empty() ) {
    229243                                                mangleName << "_";
    230                                                 for ( const Expression * param : params ) {
    231                                                         const TypeExpr * paramType = dynamic_cast< const TypeExpr * >( param );
    232                                                         assertf(paramType, "Aggregate parameters should be type expressions: %s", toCString(param));
     244                                                for ( std::list< Expression* >::const_iterator param = params.begin(); param != params.end(); ++param ) {
     245                                                        TypeExpr *paramType = dynamic_cast< TypeExpr* >( *param );
     246                                                        assertf(paramType, "Aggregate parameters should be type expressions: %s", toCString(*param));
    233247                                                        maybeAccept( paramType->type, *visitor );
    234248                                                }
     
    238252                        }
    239253
    240                         void Mangler_old::postvisit( const StructInstType * aggregateUseType ) {
    241                                 mangleRef( aggregateUseType, Encoding::struct_t );
    242                         }
    243 
    244                         void Mangler_old::postvisit( const UnionInstType * aggregateUseType ) {
    245                                 mangleRef( aggregateUseType, Encoding::union_t );
    246                         }
    247 
    248                         void Mangler_old::postvisit( const EnumInstType * aggregateUseType ) {
    249                                 mangleRef( aggregateUseType, Encoding::enum_t );
    250                         }
    251 
    252                         void Mangler_old::postvisit( const TypeInstType * typeInst ) {
     254                        void Mangler::postvisit( StructInstType * aggregateUseType ) {
     255                                mangleRef( aggregateUseType, "s" );
     256                        }
     257
     258                        void Mangler::postvisit( UnionInstType * aggregateUseType ) {
     259                                mangleRef( aggregateUseType, "u" );
     260                        }
     261
     262                        void Mangler::postvisit( EnumInstType * aggregateUseType ) {
     263                                mangleRef( aggregateUseType, "e" );
     264                        }
     265
     266                        void Mangler::postvisit( TypeInstType * typeInst ) {
    253267                                VarMapType::iterator varNum = varNums.find( typeInst->get_name() );
    254268                                if ( varNum == varNums.end() ) {
    255                                         mangleRef( typeInst, Encoding::type );
     269                                        mangleRef( typeInst, "t" );
    256270                                } else {
    257271                                        printQualifiers( typeInst );
    258                                         // Note: Can't use name here, since type variable names do not actually disambiguate a function, e.g.
    259                                         //   forall(dtype T) void f(T);
    260                                         //   forall(dtype S) void f(S);
    261                                         // are equivalent and should mangle the same way. This is accomplished by numbering the type variables when they
    262                                         // are first found and prefixing with the appropriate encoding for the type class.
    263                                         assertf( varNum->second.second < TypeDecl::NUMBER_OF_KINDS, "Unhandled type variable kind: %d", varNum->second.second );
    264                                         mangleName << Encoding::typeVariables[varNum->second.second] << varNum->second.first;
     272                                        std::ostringstream numStream;
     273                                        numStream << varNum->second.first;
     274                                        switch ( (TypeDecl::Kind )varNum->second.second ) {
     275                                          case TypeDecl::Dtype:
     276                                                mangleName << "d";
     277                                                break;
     278                                          case TypeDecl::Ftype:
     279                                                mangleName << "f";
     280                                                break;
     281                                                case TypeDecl::Ttype:
     282                                                mangleName << "tVARGS";
     283                                                break;
     284                                                default:
     285                                                assert( false );
     286                                        } // switch
     287                                        mangleName << numStream.str();
    265288                                } // if
    266289                        }
    267290
    268                         void Mangler_old::postvisit( const TraitInstType * inst ) {
     291                        void Mangler::postvisit( TraitInstType * inst ) {
    269292                                printQualifiers( inst );
    270                                 mangleName << inst->name.size() << inst->name;
    271                         }
    272 
    273                         void Mangler_old::postvisit( const TupleType * tupleType ) {
     293                                mangleName << "_Y" << inst->name << "_";
     294                        }
     295
     296                        void Mangler::postvisit( TupleType * tupleType ) {
    274297                                printQualifiers( tupleType );
    275                                 mangleName << Encoding::tuple << tupleType->types.size();
     298                                mangleName << "T";
    276299                                acceptAll( tupleType->types, *visitor );
    277                         }
    278 
    279                         void Mangler_old::postvisit( const VarArgsType * varArgsType ) {
     300                                mangleName << "_";
     301                        }
     302
     303                        void Mangler::postvisit( VarArgsType * varArgsType ) {
    280304                                printQualifiers( varArgsType );
    281                                 static const std::string vargs = "__builtin_va_list";
    282                                 mangleName << Encoding::type << vargs.size() << vargs;
    283                         }
    284 
    285                         void Mangler_old::postvisit( const ZeroType * ) {
    286                                 mangleName << Encoding::zero;
    287                         }
    288 
    289                         void Mangler_old::postvisit( const OneType * ) {
    290                                 mangleName << Encoding::one;
    291                         }
    292 
    293                         void Mangler_old::postvisit( const QualifiedType * qualType ) {
    294                                 bool inqual = inQualifiedType;
    295                                 if (! inqual ) {
    296                                         // N marks the start of a qualified type
    297                                         inQualifiedType = true;
    298                                         mangleName << Encoding::qualifiedTypeStart;
    299                                 }
    300                                 maybeAccept( qualType->parent, *visitor );
    301                                 maybeAccept( qualType->child, *visitor );
    302                                 if ( ! inqual ) {
    303                                         // E marks the end of a qualified type
    304                                         inQualifiedType = false;
    305                                         mangleName << Encoding::qualifiedTypeEnd;
    306                                 }
    307                         }
    308 
    309                         void Mangler_old::postvisit( const TypeDecl * decl ) {
    310                                 // TODO: is there any case where mangling a TypeDecl makes sense? If so, this code needs to be
    311                                 // fixed to ensure that two TypeDecls mangle to the same name when they are the same type and vice versa.
    312                                 // Note: The current scheme may already work correctly for this case, I have not thought about this deeply
    313                                 // and the case has not yet come up in practice. Alternatively, if not then this code can be removed
    314                                 // aside from the assert false.
    315                                 assertf(false, "Mangler_old should not visit typedecl: %s", toCString(decl));
    316                                 assertf( decl->kind < TypeDecl::NUMBER_OF_KINDS, "Unhandled type variable kind: %d", decl->kind );
    317                                 mangleName << Encoding::typeVariables[ decl->kind ] << ( decl->name.length() ) << decl->name;
     305                                mangleName << "VARGS";
     306                        }
     307
     308                        void Mangler::postvisit( ZeroType * ) {
     309                                mangleName << "Z";
     310                        }
     311
     312                        void Mangler::postvisit( OneType * ) {
     313                                mangleName << "O";
     314                        }
     315
     316                        void Mangler::postvisit( TypeDecl * decl ) {
     317                                static const char *typePrefix[] = { "BT", "BD", "BF" };
     318                                mangleName << typePrefix[ decl->get_kind() ] << ( decl->name.length() + 1 ) << decl->name;
    318319                        }
    319320
     
    324325                        }
    325326
    326                         void Mangler_old::printQualifiers( const Type * type ) {
     327                        void Mangler::printQualifiers( Type * type ) {
    327328                                // skip if not including qualifiers
    328329                                if ( typeMode ) return;
    329                                 if ( ! type->forall.empty() ) {
     330                                if ( ! type->get_forall().empty() ) {
    330331                                        std::list< std::string > assertionNames;
    331                                         int dcount = 0, fcount = 0, vcount = 0, acount = 0;
    332                                         mangleName << Encoding::forall;
    333                                         for ( const TypeDecl * i : type->forall ) {
    334                                                 switch ( i->kind ) {
     332                                        int tcount = 0, dcount = 0, fcount = 0, vcount = 0;
     333                                        mangleName << "A";
     334                                        for ( Type::ForallList::iterator i = type->forall.begin(); i != type->forall.end(); ++i ) {
     335                                                switch ( (*i)->get_kind() ) {
    335336                                                  case TypeDecl::Dtype:
    336337                                                        dcount++;
     
    345346                                                        assert( false );
    346347                                                } // switch
    347                                                 varNums[ i->name ] = std::make_pair( nextVarNum, (int)i->kind );
    348                                                 for ( const DeclarationWithType * assert : i->assertions ) {
    349                                                         PassVisitor<Mangler_old> sub_mangler(
    350                                                                 mangleOverridable, typeMode, mangleGenericParams, nextVarNum, varNums );
    351                                                         assert->accept( sub_mangler );
    352                                                         assertionNames.push_back( sub_mangler.pass.get_mangleName() );
    353                                                         acount++;
     348                                                varNums[ (*i)->name ] = std::pair< int, int >( nextVarNum++, (int)(*i)->get_kind() );
     349                                                for ( std::list< DeclarationWithType* >::iterator assert = (*i)->assertions.begin(); assert != (*i)->assertions.end(); ++assert ) {
     350                                                        PassVisitor<Mangler> sub_mangler( mangleOverridable, typeMode, mangleGenericParams );
     351                                                        sub_mangler.pass.nextVarNum = nextVarNum;
     352                                                        sub_mangler.pass.isTopLevel = false;
     353                                                        sub_mangler.pass.varNums = varNums;
     354                                                        (*assert)->accept( sub_mangler );
     355                                                        assertionNames.push_back( sub_mangler.pass.mangleName.str() );
    354356                                                } // for
    355357                                        } // for
    356                                         mangleName << dcount << "_" << fcount << "_" << vcount << "_" << acount << "_";
     358                                        mangleName << tcount << "_" << dcount << "_" << fcount << "_" << vcount << "_";
    357359                                        std::copy( assertionNames.begin(), assertionNames.end(), std::ostream_iterator< std::string >( mangleName, "" ) );
    358360                                        mangleName << "_";
     
    361363                                        // these qualifiers do not distinguish the outermost type of a function parameter
    362364                                        if ( type->get_const() ) {
    363                                                 mangleName << Encoding::qualifiers.at(Type::Const);
     365                                                mangleName << "C";
    364366                                        } // if
    365367                                        if ( type->get_volatile() ) {
    366                                                 mangleName << Encoding::qualifiers.at(Type::Volatile);
     368                                                mangleName << "V";
    367369                                        } // if
    368370                                        // Removed due to restrict not affecting function compatibility in GCC
     
    371373                                        // } // if
    372374                                        if ( type->get_atomic() ) {
    373                                                 mangleName << Encoding::qualifiers.at(Type::Atomic);
     375                                                mangleName << "A";
    374376                                        } // if
    375377                                }
    376378                                if ( type->get_mutex() ) {
    377                                         mangleName << Encoding::qualifiers.at(Type::Mutex);
     379                                        mangleName << "M";
    378380                                } // if
     381                                if ( type->get_lvalue() ) {
     382                                        // mangle based on whether the type is lvalue, so that the resolver can differentiate lvalues and rvalues
     383                                        mangleName << "L";
     384                                }
     385
    379386                                if ( inFunctionType ) {
    380387                                        // turn off inFunctionType so that types can be differentiated for nested qualifiers
     
    386393        } // namespace Mangler
    387394} // namespace SymTab
    388 
    389 namespace Mangle {
    390         namespace {
    391                 /// Mangles names to a unique C identifier
    392                 struct Mangler_new : public ast::WithShortCircuiting, public ast::WithVisitorRef<Mangler_new>, public ast::WithGuards {
    393                         Mangler_new( Mangle::Mode mode );
    394                         Mangler_new( const Mangler_new & ) = delete;
    395 
    396                         void previsit( const ast::Node * ) { visit_children = false; }
    397 
    398                         void postvisit( const ast::ObjectDecl * declaration );
    399                         void postvisit( const ast::FunctionDecl * declaration );
    400                         void postvisit( const ast::TypeDecl * declaration );
    401 
    402                         void postvisit( const ast::VoidType * voidType );
    403                         void postvisit( const ast::BasicType * basicType );
    404                         void postvisit( const ast::PointerType * pointerType );
    405                         void postvisit( const ast::ArrayType * arrayType );
    406                         void postvisit( const ast::ReferenceType * refType );
    407                         void postvisit( const ast::FunctionType * functionType );
    408                         void postvisit( const ast::StructInstType * aggregateUseType );
    409                         void postvisit( const ast::UnionInstType * aggregateUseType );
    410                         void postvisit( const ast::EnumInstType * aggregateUseType );
    411                         void postvisit( const ast::TypeInstType * aggregateUseType );
    412                         void postvisit( const ast::TraitInstType * inst );
    413                         void postvisit( const ast::TupleType * tupleType );
    414                         void postvisit( const ast::VarArgsType * varArgsType );
    415                         void postvisit( const ast::ZeroType * zeroType );
    416                         void postvisit( const ast::OneType * oneType );
    417                         void postvisit( const ast::QualifiedType * qualType );
    418 
    419                         std::string get_mangleName() { return mangleName.str(); }
    420                   private:
    421                         std::ostringstream mangleName;  ///< Mangled name being constructed
    422                         typedef std::map< std::string, std::pair< int, int > > VarMapType;
    423                         VarMapType varNums;             ///< Map of type variables to indices
    424                         int nextVarNum;                 ///< Next type variable index
    425                         bool isTopLevel;                ///< Is the Mangler at the top level
    426                         bool mangleOverridable;         ///< Specially mangle overridable built-in methods
    427                         bool typeMode;                  ///< Produce a unique mangled name for a type
    428                         bool mangleGenericParams;       ///< Include generic parameters in name mangling if true
    429                         bool inFunctionType = false;    ///< Include type qualifiers if false.
    430                         bool inQualifiedType = false;   ///< Add start/end delimiters around qualified type
    431 
    432                   private:
    433                         Mangler_new( bool mangleOverridable, bool typeMode, bool mangleGenericParams,
    434                                 int nextVarNum, const VarMapType& varNums );
    435                         friend class ast::Pass<Mangler_new>;
    436 
    437                   private:
    438                         void mangleDecl( const ast::DeclWithType *declaration );
    439                         void mangleRef( const ast::ReferenceToType *refType, std::string prefix );
    440 
    441                         void printQualifiers( const ast::Type *type );
    442                 }; // Mangler_new
    443         } // namespace
    444 
    445 
    446         std::string mangle( const ast::Node * decl, Mangle::Mode mode ) {
    447                 ast::Pass<Mangler_new> mangler( mode );
    448                 maybeAccept( decl, mangler );
    449                 return mangler.pass.get_mangleName();
    450         }
    451 
    452         namespace {
    453                 Mangler_new::Mangler_new( Mangle::Mode mode )
    454                         : nextVarNum( 0 ), isTopLevel( true ),
    455                         mangleOverridable  ( ! mode.no_overrideable   ),
    456                         typeMode           (   mode.type              ),
    457                         mangleGenericParams( ! mode.no_generic_params ) {}
    458 
    459                 Mangler_new::Mangler_new( bool mangleOverridable, bool typeMode, bool mangleGenericParams,
    460                         int nextVarNum, const VarMapType& varNums )
    461                         : varNums( varNums ), nextVarNum( nextVarNum ), isTopLevel( false ),
    462                         mangleOverridable( mangleOverridable ), typeMode( typeMode ),
    463                         mangleGenericParams( mangleGenericParams ) {}
    464 
    465                 void Mangler_new::mangleDecl( const ast::DeclWithType * decl ) {
    466                         bool wasTopLevel = isTopLevel;
    467                         if ( isTopLevel ) {
    468                                 varNums.clear();
    469                                 nextVarNum = 0;
    470                                 isTopLevel = false;
    471                         } // if
    472                         mangleName << Encoding::manglePrefix;
    473                         CodeGen::OperatorInfo opInfo;
    474                         if ( operatorLookup( decl->name, opInfo ) ) {
    475                                 mangleName << opInfo.outputName.size() << opInfo.outputName;
    476                         } else {
    477                                 mangleName << decl->name.size() << decl->name;
    478                         } // if
    479                         maybeAccept( decl->get_type(), *visitor );
    480                         if ( mangleOverridable && decl->linkage.is_overrideable ) {
    481                                 // want to be able to override autogenerated and intrinsic routines,
    482                                 // so they need a different name mangling
    483                                 if ( decl->linkage == ast::Linkage::AutoGen ) {
    484                                         mangleName << Encoding::autogen;
    485                                 } else if ( decl->linkage == ast::Linkage::Intrinsic ) {
    486                                         mangleName << Encoding::intrinsic;
    487                                 } else {
    488                                         // if we add another kind of overridable function, this has to change
    489                                         assert( false && "unknown overrideable linkage" );
    490                                 } // if
    491                         }
    492                         isTopLevel = wasTopLevel;
    493                 }
    494 
    495                 void Mangler_new::postvisit( const ast::ObjectDecl * decl ) {
    496                         mangleDecl( decl );
    497                 }
    498 
    499                 void Mangler_new::postvisit( const ast::FunctionDecl * decl ) {
    500                         mangleDecl( decl );
    501                 }
    502 
    503                 void Mangler_new::postvisit( const ast::VoidType * voidType ) {
    504                         printQualifiers( voidType );
    505                         mangleName << Encoding::void_t;
    506                 }
    507 
    508                 void Mangler_new::postvisit( const ast::BasicType * basicType ) {
    509                         printQualifiers( basicType );
    510                         assertf( basicType->kind < ast::BasicType::NUMBER_OF_BASIC_TYPES, "Unhandled basic type: %d", basicType->kind );
    511                         mangleName << Encoding::basicTypes[ basicType->kind ];
    512                 }
    513 
    514                 void Mangler_new::postvisit( const ast::PointerType * pointerType ) {
    515                         printQualifiers( pointerType );
    516                         // mangle void (*f)() and void f() to the same name to prevent overloading on functions and function pointers
    517                         if ( ! pointerType->base.as<ast::FunctionType>() ) mangleName << Encoding::pointer;
    518                         maybe_accept( pointerType->base.get(), *visitor );
    519                 }
    520 
    521                 void Mangler_new::postvisit( const ast::ArrayType * arrayType ) {
    522                         // TODO: encode dimension
    523                         printQualifiers( arrayType );
    524                         mangleName << Encoding::array << "0";
    525                         maybeAccept( arrayType->base.get(), *visitor );
    526                 }
    527 
    528                 void Mangler_new::postvisit( const ast::ReferenceType * refType ) {
    529                         // don't print prefix (e.g. 'R') for reference types so that references and non-references do not overload.
    530                         // Further, do not print the qualifiers for a reference type (but do run printQualifers because of TypeDecls, etc.),
    531                         // by pretending every reference type is a function parameter.
    532                         GuardValue( inFunctionType );
    533                         inFunctionType = true;
    534                         printQualifiers( refType );
    535                         maybeAccept( refType->base.get(), *visitor );
    536                 }
    537 
    538                 inline std::vector< ast::ptr< ast::Type > > getTypes( const std::vector< ast::ptr< ast::DeclWithType > > & decls ) {
    539                         std::vector< ast::ptr< ast::Type > > ret;
    540                         std::transform( decls.begin(), decls.end(), std::back_inserter( ret ),
    541                                                         std::mem_fun( &ast::DeclWithType::get_type ) );
    542                         return ret;
    543                 }
    544 
    545                 void Mangler_new::postvisit( const ast::FunctionType * functionType ) {
    546                         printQualifiers( functionType );
    547                         mangleName << Encoding::function;
    548                         // turn on inFunctionType so that printQualifiers does not print most qualifiers for function parameters,
    549                         // since qualifiers on outermost parameter type do not differentiate function types, e.g.,
    550                         // void (*)(const int) and void (*)(int) are the same type, but void (*)(const int *) and void (*)(int *) are different
    551                         GuardValue( inFunctionType );
    552                         inFunctionType = true;
    553                         std::vector< ast::ptr< ast::Type > > returnTypes = getTypes( functionType->returns );
    554                         if (returnTypes.empty()) mangleName << Encoding::void_t;
    555                         else accept_each( returnTypes, *visitor );
    556                         mangleName << "_";
    557                         std::vector< ast::ptr< ast::Type > > paramTypes = getTypes( functionType->params );
    558                         accept_each( paramTypes, *visitor );
    559                         mangleName << "_";
    560                 }
    561 
    562                 void Mangler_new::mangleRef( const ast::ReferenceToType * refType, std::string prefix ) {
    563                         printQualifiers( refType );
    564 
    565                         mangleName << prefix << refType->name.length() << refType->name;
    566 
    567                         if ( mangleGenericParams ) {
    568                                 if ( ! refType->params.empty() ) {
    569                                         mangleName << "_";
    570                                         for ( const ast::Expr * param : refType->params ) {
    571                                                 auto paramType = dynamic_cast< const ast::TypeExpr * >( param );
    572                                                 assertf(paramType, "Aggregate parameters should be type expressions: %s", toCString(param));
    573                                                 maybeAccept( paramType->type.get(), *visitor );
    574                                         }
    575                                         mangleName << "_";
    576                                 }
    577                         }
    578                 }
    579 
    580                 void Mangler_new::postvisit( const ast::StructInstType * aggregateUseType ) {
    581                         mangleRef( aggregateUseType, Encoding::struct_t );
    582                 }
    583 
    584                 void Mangler_new::postvisit( const ast::UnionInstType * aggregateUseType ) {
    585                         mangleRef( aggregateUseType, Encoding::union_t );
    586                 }
    587 
    588                 void Mangler_new::postvisit( const ast::EnumInstType * aggregateUseType ) {
    589                         mangleRef( aggregateUseType, Encoding::enum_t );
    590                 }
    591 
    592                 void Mangler_new::postvisit( const ast::TypeInstType * typeInst ) {
    593                         VarMapType::iterator varNum = varNums.find( typeInst->name );
    594                         if ( varNum == varNums.end() ) {
    595                                 mangleRef( typeInst, Encoding::type );
    596                         } else {
    597                                 printQualifiers( typeInst );
    598                                 // Note: Can't use name here, since type variable names do not actually disambiguate a function, e.g.
    599                                 //   forall(dtype T) void f(T);
    600                                 //   forall(dtype S) void f(S);
    601                                 // are equivalent and should mangle the same way. This is accomplished by numbering the type variables when they
    602                                 // are first found and prefixing with the appropriate encoding for the type class.
    603                                 assertf( varNum->second.second < TypeDecl::NUMBER_OF_KINDS, "Unhandled type variable kind: %d", varNum->second.second );
    604                                 mangleName << Encoding::typeVariables[varNum->second.second] << varNum->second.first;
    605                         } // if
    606                 }
    607 
    608                 void Mangler_new::postvisit( const ast::TraitInstType * inst ) {
    609                         printQualifiers( inst );
    610                         mangleName << inst->name.size() << inst->name;
    611                 }
    612 
    613                 void Mangler_new::postvisit( const ast::TupleType * tupleType ) {
    614                         printQualifiers( tupleType );
    615                         mangleName << Encoding::tuple << tupleType->types.size();
    616                         accept_each( tupleType->types, *visitor );
    617                 }
    618 
    619                 void Mangler_new::postvisit( const ast::VarArgsType * varArgsType ) {
    620                         printQualifiers( varArgsType );
    621                         static const std::string vargs = "__builtin_va_list";
    622                         mangleName << Encoding::type << vargs.size() << vargs;
    623                 }
    624 
    625                 void Mangler_new::postvisit( const ast::ZeroType * ) {
    626                         mangleName << Encoding::zero;
    627                 }
    628 
    629                 void Mangler_new::postvisit( const ast::OneType * ) {
    630                         mangleName << Encoding::one;
    631                 }
    632 
    633                 void Mangler_new::postvisit( const ast::QualifiedType * qualType ) {
    634                         bool inqual = inQualifiedType;
    635                         if (! inqual ) {
    636                                 // N marks the start of a qualified type
    637                                 inQualifiedType = true;
    638                                 mangleName << Encoding::qualifiedTypeStart;
    639                         }
    640                         maybeAccept( qualType->parent.get(), *visitor );
    641                         maybeAccept( qualType->child.get(), *visitor );
    642                         if ( ! inqual ) {
    643                                 // E marks the end of a qualified type
    644                                 inQualifiedType = false;
    645                                 mangleName << Encoding::qualifiedTypeEnd;
    646                         }
    647                 }
    648 
    649                 void Mangler_new::postvisit( const ast::TypeDecl * decl ) {
    650                         // TODO: is there any case where mangling a TypeDecl makes sense? If so, this code needs to be
    651                         // fixed to ensure that two TypeDecls mangle to the same name when they are the same type and vice versa.
    652                         // Note: The current scheme may already work correctly for this case, I have not thought about this deeply
    653                         // and the case has not yet come up in practice. Alternatively, if not then this code can be removed
    654                         // aside from the assert false.
    655                         assertf(false, "Mangler_new should not visit typedecl: %s", toCString(decl));
    656                         assertf( decl->kind < ast::TypeVar::Kind::NUMBER_OF_KINDS, "Unhandled type variable kind: %d", decl->kind );
    657                         mangleName << Encoding::typeVariables[ decl->kind ] << ( decl->name.length() ) << decl->name;
    658                 }
    659 
    660                 __attribute__((unused)) void printVarMap( const std::map< std::string, std::pair< int, int > > &varMap, std::ostream &os ) {
    661                         for ( std::map< std::string, std::pair< int, int > >::const_iterator i = varMap.begin(); i != varMap.end(); ++i ) {
    662                                 os << i->first << "(" << i->second.first << "/" << i->second.second << ")" << std::endl;
    663                         } // for
    664                 }
    665 
    666                 void Mangler_new::printQualifiers( const ast::Type * type ) {
    667                         // skip if not including qualifiers
    668                         if ( typeMode ) return;
    669                         if ( auto ptype = dynamic_cast< const ast::ParameterizedType * >(type) ) {
    670                                 if ( ! ptype->forall.empty() ) {
    671                                         std::list< std::string > assertionNames;
    672                                         int dcount = 0, fcount = 0, vcount = 0, acount = 0;
    673                                         mangleName << Encoding::forall;
    674                                         for ( const ast::TypeDecl * decl : ptype->forall ) {
    675                                                 switch ( decl->kind ) {
    676                                                 case ast::TypeVar::Kind::Dtype:
    677                                                         dcount++;
    678                                                         break;
    679                                                 case ast::TypeVar::Kind::Ftype:
    680                                                         fcount++;
    681                                                         break;
    682                                                 case ast::TypeVar::Kind::Ttype:
    683                                                         vcount++;
    684                                                         break;
    685                                                 default:
    686                                                         assert( false );
    687                                                 } // switch
    688                                                 varNums[ decl->name ] = std::make_pair( nextVarNum, (int)decl->kind );
    689                                                 for ( const ast::DeclWithType * assert : decl->assertions ) {
    690                                                         ast::Pass<Mangler_new> sub_mangler(
    691                                                                 mangleOverridable, typeMode, mangleGenericParams, nextVarNum, varNums );
    692                                                         assert->accept( sub_mangler );
    693                                                         assertionNames.push_back( sub_mangler.pass.get_mangleName() );
    694                                                         acount++;
    695                                                 } // for
    696                                         } // for
    697                                         mangleName << dcount << "_" << fcount << "_" << vcount << "_" << acount << "_";
    698                                         std::copy( assertionNames.begin(), assertionNames.end(), std::ostream_iterator< std::string >( mangleName, "" ) );
    699                                         mangleName << "_";
    700                                 } // if
    701                         } // if
    702                         if ( ! inFunctionType ) {
    703                                 // these qualifiers do not distinguish the outermost type of a function parameter
    704                                 if ( type->is_const() ) {
    705                                         mangleName << Encoding::qualifiers.at(Type::Const);
    706                                 } // if
    707                                 if ( type->is_volatile() ) {
    708                                         mangleName << Encoding::qualifiers.at(Type::Volatile);
    709                                 } // if
    710                                 // Removed due to restrict not affecting function compatibility in GCC
    711                                 // if ( type->get_isRestrict() ) {
    712                                 //      mangleName << "E";
    713                                 // } // if
    714                                 if ( type->is_atomic() ) {
    715                                         mangleName << Encoding::qualifiers.at(Type::Atomic);
    716                                 } // if
    717                         }
    718                         if ( type->is_mutex() ) {
    719                                 mangleName << Encoding::qualifiers.at(Type::Mutex);
    720                         } // if
    721                         if ( inFunctionType ) {
    722                                 // turn off inFunctionType so that types can be differentiated for nested qualifiers
    723                                 GuardValue( inFunctionType );
    724                                 inFunctionType = false;
    725                         }
    726                 }
    727         }       // namespace
    728 } // namespace Mangle
    729395
    730396// Local Variables: //
Note: See TracChangeset for help on using the changeset viewer.