Ignore:
Timestamp:
Aug 27, 2018, 4:40:34 PM (7 years ago)
Author:
Rob Schluntz <rschlunt@…>
Branches:
ADT, arm-eh, ast-experimental, cleanup-dtors, enum, forall-pointer-decay, jacob/cs343-translation, jenkins-sandbox, master, new-ast, new-ast-unique-expr, pthread-emulation, qualifiedEnum
Children:
b7c89aa
Parents:
f9feab8 (diff), 305581d (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
Message:

Merge branch 'master' into cleanup-dtors

File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/CodeGen/CodeGenerator.cc

    rf9feab8 r90152a4  
    1010// Created On       : Mon May 18 07:44:20 2015
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Sun Sep  3 20:42:52 2017
    13 // Update Count     : 490
     12// Last Modified On : Sat May  5 09:08:32 2018
     13// Update Count     : 494
    1414//
    1515#include "CodeGenerator.h"
     
    1818#include <list>                      // for _List_iterator, list, list<>::it...
    1919
    20 #include "Common/SemanticError.h"    // for SemanticError
    2120#include "Common/UniqueName.h"       // for UniqueName
    2221#include "Common/utility.h"          // for CodeLocation, toString
     
    117116        }
    118117
    119         CodeGenerator::CodeGenerator( std::ostream & os, bool pretty, bool genC, bool lineMarks ) : indent( CodeGenerator::tabsize ), output( os ), printLabels( *this ), pretty( pretty ), genC( genC ), lineMarks( lineMarks ), endl( *this ) {}
     118        CodeGenerator::CodeGenerator( std::ostream & os, bool pretty, bool genC, bool lineMarks, bool printExprTypes ) : indent( CodeGenerator::tabsize ), output( os ), printLabels( *this ), pretty( pretty ), genC( genC ), lineMarks( lineMarks ), printExprTypes( printExprTypes ), endl( *this ) {}
    120119
    121120        string CodeGenerator::mangleName( DeclarationWithType * decl ) {
    122                 if ( pretty ) return decl->get_name();
    123                 if ( decl->get_mangleName() != "" ) {
     121                // GCC builtins should always be printed unmangled
     122                if ( pretty || decl->linkage.is_gcc_builtin ) return decl->name;
     123                if ( decl->mangleName != "" ) {
    124124                        // need to incorporate scope level in order to differentiate names for destructors
    125125                        return decl->get_scopedMangleName();
    126126                } else {
    127                         return decl->get_name();
     127                        return decl->name;
    128128                } // if
    129129        }
     
    133133                output << "__attribute__ ((";
    134134                for ( list< Attribute * >::iterator attr( attributes.begin() );; ) {
    135                         output << (*attr)->get_name();
    136                         if ( ! (*attr)->get_parameters().empty() ) {
     135                        output << (*attr)->name;
     136                        if ( ! (*attr)->parameters.empty() ) {
    137137                                output << "(";
    138                                 genCommaList( (*attr)->get_parameters().begin(), (*attr)->get_parameters().end() );
     138                                genCommaList( (*attr)->parameters.begin(), (*attr)->parameters.end() );
    139139                                output << ")";
    140140                        } // if
     
    160160        }
    161161
     162        // *** Expression
     163        void CodeGenerator::previsit( Expression * node ) {
     164                previsit( (BaseSyntaxNode *)node );
     165                GuardAction( [this, node](){
     166                        if ( printExprTypes && node->result ) {
     167                                output << " /* " << genType( node->result, "", pretty, genC ) << " */ ";
     168                        }
     169                } );
     170        }
     171
    162172        // *** Declarations
    163173        void CodeGenerator::postvisit( FunctionDecl * functionDecl ) {
     174                // deleted decls should never be used, so don't print them
     175                if ( functionDecl->isDeleted && genC ) return;
    164176                extension( functionDecl );
    165177                genAttributes( functionDecl->get_attributes() );
     
    175187                        functionDecl->get_statements()->accept( *visitor );
    176188                } // if
     189                if ( functionDecl->isDeleted ) {
     190                        output << " = void";
     191                }
    177192        }
    178193
    179194        void CodeGenerator::postvisit( ObjectDecl * objectDecl ) {
     195                // deleted decls should never be used, so don't print them
     196                if ( objectDecl->isDeleted && genC ) return;
    180197                if (objectDecl->get_name().empty() && genC ) {
    181198                        // only generate an anonymous name when generating C code, otherwise it clutters the output too much
     
    196213                        objectDecl->get_init()->accept( *visitor );
    197214                } // if
     215                if ( objectDecl->isDeleted ) {
     216                        output << " = void";
     217                }
    198218
    199219                if ( objectDecl->get_bitfieldWidth() ) {
     
    204224
    205225        void CodeGenerator::handleAggregate( AggregateDecl * aggDecl, const std::string & kind ) {
    206                 genAttributes( aggDecl->get_attributes() );
    207 
    208                 if( ! aggDecl->get_parameters().empty() && ! genC ) {
     226                if( ! aggDecl->parameters.empty() && ! genC ) {
    209227                        // assertf( ! genC, "Aggregate type parameters should not reach code generation." );
    210228                        output << "forall(";
    211                         genCommaList( aggDecl->get_parameters().begin(), aggDecl->get_parameters().end() );
     229                        genCommaList( aggDecl->parameters.begin(), aggDecl->parameters.end() );
    212230                        output << ")" << endl;
    213231                        output << indent;
    214232                }
    215233
    216                 output << kind << aggDecl->get_name();
     234                output << kind;
     235                genAttributes( aggDecl->attributes );
     236                output << aggDecl->name;
    217237
    218238                if ( aggDecl->has_body() ) {
    219                         std::list< Declaration * > & memb = aggDecl->get_members();
     239                        std::list< Declaration * > & memb = aggDecl->members;
    220240                        output << " {" << endl;
    221241
     
    299319                        output << " }";
    300320                }
     321        }
     322
     323        void CodeGenerator::postvisit( StaticAssertDecl * assertDecl ) {
     324                output << "_Static_assert(";
     325                assertDecl->condition->accept( *visitor );
     326                output << ", ";
     327                assertDecl->message->accept( *visitor );
     328                output << ")";
    301329        }
    302330
     
    353381
    354382        void CodeGenerator::postvisit( Constant * constant ) {
    355                 output << constant->get_value() ;
     383                output << constant->get_value();
    356384        }
    357385
     
    570598                output << "(";
    571599                if ( castExpr->get_result()->isVoid() ) {
    572                         output << "(void)" ;
     600                        output << "(void)";
    573601                } else {
    574602                        // at least one result type of cast.
     
    579607                        output << ")";
    580608                } // if
    581                 castExpr->get_arg()->accept( *visitor );
     609                castExpr->arg->accept( *visitor );
     610                output << ")";
     611        }
     612
     613        void CodeGenerator::postvisit( KeywordCastExpr * castExpr ) {
     614                assertf( ! genC, "KeywordCast should not reach code generation." );
     615                extension( castExpr );
     616                output << "((" << castExpr->targetString() << " &)";
     617                castExpr->arg->accept( *visitor );
    582618                output << ")";
    583619        }
     
    764800
    765801        void CodeGenerator::postvisit( StmtExpr * stmtExpr ) {
    766                 std::list< Statement * > & stmts = stmtExpr->get_statements()->get_kids();
     802                std::list< Statement * > & stmts = stmtExpr->statements->kids;
    767803                output << "({" << endl;
    768804                ++indent;
     
    775811                                // cannot cast to void, otherwise the expression statement has no value
    776812                                if ( ExprStmt * exprStmt = dynamic_cast< ExprStmt * >( stmt ) ) {
    777                                         exprStmt->get_expr()->accept( *visitor );
     813                                        exprStmt->expr->accept( *visitor );
    778814                                        output << ";" << endl;
    779815                                        ++i;
     
    796832                expr->callExpr->accept( *visitor );
    797833        }
     834
     835        void CodeGenerator::postvisit( DeletedExpr * expr ) {
     836                assertf( ! genC, "Deleted expressions should not reach code generation." );
     837                expr->expr->accept( *visitor );
     838        }
     839
     840        void CodeGenerator::postvisit( DefaultArgExpr * arg ) {
     841                assertf( ! genC, "Default argument expressions should not reach code generation." );
     842                arg->expr->accept( *visitor );
     843        }
     844
     845        void CodeGenerator::postvisit( GenericExpr * expr ) {
     846                assertf( ! genC, "C11 _Generic expressions should not reach code generation." );
     847                output << "_Generic(";
     848                expr->control->accept( *visitor );
     849                output << ", ";
     850                unsigned int numAssocs = expr->associations.size();
     851                unsigned int i = 0;
     852                for ( GenericExpr::Association & assoc : expr->associations ) {
     853                        if (assoc.isDefault) {
     854                                output << "default: ";
     855                        } else {
     856                                output << genType( assoc.type, "", pretty, genC ) << ": ";
     857                        }
     858                        assoc.expr->accept( *visitor );
     859                        if ( i+1 != numAssocs ) {
     860                                output << ", ";
     861                        }
     862                        i++;
     863                }
     864                output << ")";
     865        }
     866
    798867
    799868        // *** Statements
     
    848917                        } // for
    849918                } // if
    850                 output << " );" ;
     919                output << " );";
    851920        }
    852921
     
    856925                output << "( ";
    857926                if ( asmStmt->get_instruction() ) asmStmt->get_instruction()->accept( *visitor );
    858                 output << " )" ;
     927                output << " )";
     928        }
     929
     930        void CodeGenerator::postvisit( DirectiveStmt * dirStmt ) {
     931                output << endl << dirStmt->directive;                   // endl prevents spaces before directive
    859932        }
    860933
     
    873946
    874947        void CodeGenerator::postvisit( SwitchStmt * switchStmt ) {
    875                 output << "switch ( " ;
     948                output << "switch ( ";
    876949                switchStmt->get_condition()->accept( *visitor );
    877950                output << " ) ";
     
    899972                ++indent;
    900973                for ( std::list<Statement *>::iterator i = sts.begin(); i != sts.end();  i++) {
    901                         output << indent << printLabels( (*i)->get_labels() )  ;
     974                        output << indent << printLabels( (*i)->get_labels() ) ;
    902975                        (*i)->accept( *visitor );
    903976                        output << endl;
     
    924997                        output << "continue";
    925998                        break;
     999                  case BranchStmt::FallThrough:
     1000                  case BranchStmt::FallThroughDefault:
     1001                        assertf( ! genC, "fallthru should not reach code generation." );
     1002                  output << "fallthru";
     1003                        break;
    9261004                } // switch
     1005                // print branch target for labelled break/continue/fallthru in debug mode
     1006                if ( ! genC && branchStmt->get_type() != BranchStmt::Goto ) {
     1007                        if ( ! branchStmt->get_target().empty() ) {
     1008                                output << " " << branchStmt->get_target();
     1009                        } else if ( branchStmt->get_type() == BranchStmt::FallThrough ) {
     1010                                output << " default";
     1011                        }
     1012                }
    9271013                output << ";";
    9281014        }
     
    10231109        void CodeGenerator::postvisit( WhileStmt * whileStmt ) {
    10241110                if ( whileStmt->get_isDoWhile() ) {
    1025                         output << "do" ;
     1111                        output << "do";
    10261112                } else {
    1027                         output << "while (" ;
     1113                        output << "while (";
    10281114                        whileStmt->get_condition()->accept( *visitor );
    10291115                        output << ")";
     
    10371123
    10381124                if ( whileStmt->get_isDoWhile() ) {
    1039                         output << " while (" ;
     1125                        output << " while (";
    10401126                        whileStmt->get_condition()->accept( *visitor );
    10411127                        output << ");";
Note: See TracChangeset for help on using the changeset viewer.