oonski94 (1158312), страница 2
Текст из файла (страница 2)
The SgProject constructor takes the .proj le (a newline-delimited list of .dep les) as an argument, and initializesa SgProject object by loading each of the .dep les:main(){SgProject P("MyProject.proj"); // opens and initializes projectfor (int i = 0; i < P.numberOfFiles(); i++){printf("Working on file %s...\n", P.fileName(i)");// begin transformation of P.file(i) here;}}Each .dep le contains a program tree for the code in the source le it represents.
The root of thetree in each le is called the global node and its immediate children are the top level denitions andfunctions in the le. Each .dep le also contains a symbol table and a type table; these will be describedbelow.The class representing les, SgFile, provides access to each of these top level denitions and to thesymbol and type tables (see Figure 1). SgFile member functions can save the restructured program toa standard output stream, string buer, ASCII le, or .dep le.
A .dep le can be unparsed back intosource code by using the unparse utility.3.3 StatementsThe Sage++ statement classes are used to represent the basic units of Fortran and C programs. Sage++has 53 dierent statement classes divided into ve categories: structured header denitions like functions,modules and classes; traditional structured control statements like do loops and conditionals; executablestatements like C expressions and subroutine calls; simple control statements like goto and return; anddeclarations and miscellaneous Fortran statements like USE, PARAMETER, and I/O statements. Mostof the statement class hierarchy is shown in the table at the end of this paper.The top-level statement class contains member functions that are applicable to all statements.
Thesubclasses add special constructors and access functions. Each statement has several standard attributes,accessible by methods of the top-level class. A source line number, a unique identier, and a varianttag which identies the subclass of the statement are attributes of statements. There can also be up tothree expressions directly associated with any statement.
The C for statement is a good example of whythree expressions are needed: for(expr 1; expr 2; expr 3)fg. Since the basic Sage++ building block is astatement, labels and comments are linked to the preceding statement.Each statement also has a context, accessible through the top-level statement class: it may have alexical predecessor and successor, and it may be nested within a control block of another statement orin a block structured denition like a C struct.
This enclosing statement is called the control parent andit denes the basic structure of the program tree.To illustrate the use of the statement classes consider the following simple example. Suppose we wishto traverse a le and apply an unrolling transformation to all the innermost loops whose bodies consistonly of assignment statements. The function is shown below:void UnrollLoops(SgFile *file, int unroll_factor){SgStatement *s = file->firstStatement();SgForStmt *loop;while(s){if (loop = isSgForStmt(s)) {SgForStmt *inner;inner = loop->getInnermostLoop();if (inner->isAssignLoop()) inner->unrollLoop(unroll_factor);}s = s->lexNext(); // the lexical successor of statement s.}}This function illustrates a typical Sage++ program; the main body of the function traverses thestatements in lexical order.
The variable s is a pointer to a generic statement object. There are twoways to tell if a statement is a loop: check to see if the variant is FOR NODE or use a special castingfunction, in this case isSgForStmt(). A function of the typeSgSUBCLASS * isSgSUBCLASS( SgBASECLASS *)is provided for each subclass of SgStatement, SgExpression and SgType.
These functions check thevariant of the argument. If the object is of the derived type SgSUBCLASS, the function returns apointer to the object, cast to SgSUBCLASS* (thus permitting access to the special member functionsof SgSUBCLASS). Otherwise, it returns NULL.3.4 ExpressionsExpressions are represented by trees of objects from the Sage++ expression class. These trees are eitherdegree two (for binary operators) or one (for unary operators).The base class for expressions, SgExpression, contains methods common to all expressions.
Everyexpression may have up to two operands: a left hand side lhs() and a right hand side rhs(). In addition,each expression has a type and it may have a symbol. The member functions of SgExpression allow theprogrammer to inspect and modify these elds.In addition, there are special methods that manipulate an entire expression tree whose root is agiven node. For example, replaceSymbolByExpression() searches an expression for symbol referencesand replaces them with an expression.
To help with building dependence analysis modules, there is amethod which will simplify linear algebraic expressions to a normal form and another which will extractthe integer coecient of a symbol in a linear expression.The hierarchy of Sage++ classes for expressions is shown in the table at the end of this paper. Unlikethe classes representing statements, there is not a subclass for every kind of expression. Expressionnodes that have their own subclass have a special type of constructor or special elds. The standardbinary operators have not been given explicit expression subclasses.
Instead, these operators have beenoverloaded as \friends" of the expression class, so building expressions containing them is a very simpletask. For example, to build an expression of the form( + 3) + 6 4XY:we need two symbol objects and two value expression objects:SgVariableSymb xsymb("X"), ysymb("Y");SgVarRefExpx(xsymb), y(ysymb);SgValueExpthree(3), fltvalue(6.4);SgExpression &e = (x + three)*y + fltvalue;The variables X and Y are created as symbols, then variable reference expressions to the symbolsare created through SgVarRefExp objects.
Notice that we have not given types to the variables X andY, and their declarations have not been generated. We will return to that in the next section. In thiscode, e is now a reference to the root (+) of the program tree for the desired expression(see Figure 2).Also note that the constructors for the value expression class allow any base type value to be created:SgValueExp(int value);SgValueExp(char char_val);SgValueExp(float float_val);SgValueExp(double double_val);SgValueExp(char *string_val);SgValueExp(double real, double imaginary);SgValueExp(SgValueExp &real, SgValueExp &imaginary);To build a C assignment statement of the formX= ( + 3) + 6 4;XY:using the denitions for variables X, Y, three, and tvalue given above, we rst construct an SgAssignOpexpression and then use it to build an SgCExpStmt object:SgCExpStmt c_stmt(SgAssignOp(x.copy(), (x + three)*y + fltvalue));In Fortran, there are no assignment expressions and we build a statement directly:SgAssignStmt fortran_stmt(x.copy(), (x + three)*y + fltvalue);The expression subclasses provide constructors that make it easy to build expressions and extractvalues.
For example, the constructors for the class SgArrayRefExp, used for array references, makebuilding array references simple.Sage++ Program Tree forX = (X + 3) * Y + 6.4;SgCExpStmtSgExprListExpSgExpressionEXPR_STMT_NODEEXPR_LISTASSGN_OPexp1exp2exp3lhsrhslhsrhsSgExpressionADD_OPlhsrhsSgVarRefExpVAR_REFsymbolSgExpressionSgValueExpMULT_OPFLOAT_VALlhsrhsVALUE = 6.4SgExprListExpSgVarRefExpEXPR_LISTVAR_REFlhsrhssymbolSgExpressionADD_OPlhsrhsSgVarRefExpSgValueExpVAR_REFINT_VALsymbolVALUE = 3SgVariableSymbSgVariableSymbVARIABLE_NAMEVARIABLE_NAME"X"next_symbol"Y"Figure 2: Program Tree Segmentnext_symbolSgArrayRefExp(SgSymbol &s, SgExpression &sub1, SgExpression &sub2,SgExpression &sub3);builds a 3-D array reference to an array with symbol s and three subscript expressions.
As anotherexample, vector expressions in Fortran (and our extension to C) are of the form exp1 : exp2 : exp3 andare represented with the SgSubscriptExp class, which has a constructor of the formSgSubscriptExp(SgExpression &lbound, SgExpression &ubound,SgExpression &step)as well as access functions to extract the three arguments. So, to build the Fortran 90 array referenceX(1:100:3) or the \extended" C array reference X[1:100:3] we can writeSgVariableSymb xsymb("X");SgValueExp three(3), one(1), hundred(100);SgSubscriptExp range(one, hundred, three);SgArrayRefExp new_expression(xsymb, range);3.5 Symbols and Types3.5.1 SymbolsThe Sage++ base class for symbols is SgSymbol.
The symbols in each le are organized as a list whichis accessible from SgFile. Every symbol has a unique identier(), a type(), which is described in detailbelow, and a statement called scope(), which is the statement in which the declaration is scoped (i.e.the control parent of the declaration statement).
The statement where the variable is declared is givenby declaredInStmt().SgSymbol has three methods for generating copies of a symbol. The simplest method copies only thesymbol table entry. Another function copies the symbol and generates new type information, and thethird methods copies the declaration body too. For Fortran 90 symbols, the attributes can be inspectedor modied.There are relatively few symbol subclasses: SgVariableSymb represents basic program variable names. It has methods which return thenumber of uses of the variable, and the statements and expressions where it is used.