Open64 (mfef90, whirl2f, and IR tools)  TAG: version-openad; SVN changeset: 916
opt_goto.h
Go to the documentation of this file.
00001 /*
00002 
00003   Copyright (C) 2000, 2001 Silicon Graphics, Inc.  All Rights Reserved.
00004 
00005   This program is free software; you can redistribute it and/or modify it
00006   under the terms of version 2 of the GNU General Public License as
00007   published by the Free Software Foundation.
00008 
00009   This program is distributed in the hope that it would be useful, but
00010   WITHOUT ANY WARRANTY; without even the implied warranty of
00011   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  
00012 
00013   Further, this software is distributed without any warranty that it is
00014   free of the rightful claim of any third person regarding infringement 
00015   or the like.  Any license provided herein, whether implied or 
00016   otherwise, applies only to this software file.  Patent licenses, if 
00017   any, provided herein do not apply to combinations of this program with 
00018   other software, or any other product whatsoever.  
00019 
00020   You should have received a copy of the GNU General Public License along
00021   with this program; if not, write the Free Software Foundation, Inc., 59
00022   Temple Place - Suite 330, Boston MA 02111-1307, USA.
00023 
00024   Contact information:  Silicon Graphics, Inc., 1600 Amphitheatre Pky,
00025   Mountain View, CA 94043, or:
00026 
00027   http://www.sgi.com
00028 
00029   For further information regarding this notice, see:
00030 
00031   http://oss.sgi.com/projects/GenInfo/NoticeExplan
00032 
00033 */
00034 
00035 
00036 //-*-c++-*-
00037 //                     Promote Gotos to Loops and IFs 
00038 //                     ------------------------------
00039 //
00040 // Description:
00041 //
00042 //     Promote gotos to loops and ifs.  This is loosely based on the
00043 //     McGill paper.  See the .cxx file for more details.
00044 //
00045 //
00046 //
00047 // Exported types and functions:
00048 //
00049 //     GOTO_TABLE
00050 //
00051 //              A table of goto_descriptors
00052 //
00053 //          GOTO_TABLE(WN *func_nd, MEM_POOL *pool)
00054 //
00055 //              Build a descriptor table.  
00056 //
00057 //          void Remove_Gotos()
00058 //
00059 //              Get rid of the gotos.
00060 //
00061 //          void Print(FILE *fp)
00062 //
00063 //      GOTO_DESCRIPTOR
00064 //
00065 //              Describe the goto.
00066 //
00067 //          WN *Goto_Wn
00068 //
00069 //              The wn of the goto.
00070 //
00071 //          WN *Label_Wn
00072 //
00073 //              The wn of the corresponding label
00074 //
00075 //          INT Goto_Offset, Label_Offset
00076 //
00077 //              The offsets of the goto and its corresponding
00078 //              label as defined in the paper.
00079 //
00080 //          GOTO_DESCRIPTOR(WN *wn,WN *label_wn,
00081 //                              INT goto_offset,INT label_offset) 
00082 //
00083 //          BOOL Is_Dismantled
00084 //
00085 //              Does the goto still exist
00086 //
00087 //      LABEL_DESCRIPTOR
00088 //
00089 //              Describe a label
00090 //
00091 //          WN *Label_Wn
00092 //
00093 //              The wn of the label
00094 //
00095 //          INT Offset
00096 //
00097 //              The offset as defined in the paper
00098 //
00099 //          LABEL_DESCRIPTOR(WN *label_wn, INT offset)
00100 //
00101 //
00102 //      MAX_GOTO_EXPANDING_TRANSFORMATIONS = 20
00103 //
00104 //          Some of the transformations increase the code size.  In particular moving
00105 //      gotos out of IFs.  This puts in a circuit breaker to avoid the bad cases.
00106 //      
00107 //
00108 
00109 #ifndef opt_goto_INCLUDED
00110 #define opt_goto_INCLUDED "opt_goto.h"
00111 
00112 #ifdef _KEEP_RCS_ID
00113 #endif /* _KEEP_RCS_ID */
00114 
00115 #include "wn.h"
00116 #include "cxx_memory.h"
00117 #include "cxx_template.h"
00118 #include "cxx_hash.h"
00119 
00120 class GOTO_DESCRIPTOR {
00121 public:
00122   WN *Goto_Wn;
00123   WN *Label_Wn;
00124   INT Goto_Offset;
00125   INT Label_Offset;
00126   BOOL Is_Dismantled;
00127   BOOL Is_Compgoto;
00128   GOTO_DESCRIPTOR(WN *goto_wn,WN *label_wn,INT goto_offset, INT label_offset,
00129                         BOOL is_compgoto) {
00130     Goto_Wn = goto_wn;
00131     Label_Wn = label_wn;
00132     Goto_Offset = goto_offset;
00133     Label_Offset = label_offset;
00134     Is_Dismantled = FALSE;
00135     Is_Compgoto = is_compgoto;
00136   }
00137 };
00138 
00139 class LABEL_DESCRIPTOR {
00140 public:
00141   WN *Label_Wn;
00142   INT Offset;
00143   LABEL_DESCRIPTOR(WN *label_wn,INT offset) {
00144     Label_Wn = label_wn;
00145     Offset = offset;
00146   }
00147 };
00148 
00149 typedef STACK<GOTO_DESCRIPTOR> GOTO_DESCRIPTOR_STACK;
00150 typedef STACK<LABEL_DESCRIPTOR> LABEL_DESCRIPTOR_STACK;
00151 typedef STACK<WN *> GOTO_TABLE_WN_STACK;
00152 
00153 class GOTO_TABLE {
00154   GOTO_DESCRIPTOR_STACK _gd;
00155   GOTO_TABLE_WN_STACK _altentry;
00156   LABEL_DESCRIPTOR_STACK _bad_label;
00157   MEM_POOL *_pool;
00158   WN *_func_nd;
00159   HASH_TABLE<INT,LABEL_DESCRIPTOR *> *_label_table;
00160   WN_MAP _parent_map;
00161   INT _offset;
00162   BOOL _contains_altentry;
00163 public:
00164   GOTO_TABLE(WN *func_nd, MEM_POOL *pool) : _gd(pool), _bad_label(pool),
00165                                             _altentry(pool), _pool(pool) {
00166     _offset = 0;
00167     _func_nd = func_nd;
00168     _contains_altentry=FALSE;
00169     Build();
00170   }
00171   void Remove_Gotos();
00172   void Print(FILE *fp);
00173   ~GOTO_TABLE()  {  
00174     WN_MAP_Delete(_parent_map); 
00175     CXX_DELETE(_label_table,_pool);
00176   }
00177 private:
00178   WN *Get_Parent(WN *wn) const { return (WN *) WN_MAP_Get(_parent_map,wn); }
00179   void Set_Parent(WN *wn, WN *p) { WN_MAP_Set(_parent_map, wn, (void *)p); };
00180   void Build();
00181   void Build_Rec(WN *wn, WN *parent, BOOL inside_compgoto);
00182   void Fixup_Parents(WN *wn, WN *parent);
00183   void Backpatch();
00184   BOOL Ancestor_Through_If(GOTO_DESCRIPTOR *gd);
00185   BOOL Sibling(GOTO_DESCRIPTOR *gd);
00186   void Move_Goto_Out(GOTO_DESCRIPTOR *gd);
00187   void Replace_Goto_With_If(GOTO_DESCRIPTOR *gd);
00188   void Replace_Goto_With_While(GOTO_DESCRIPTOR *gd);
00189   void Move_Into_Else(GOTO_DESCRIPTOR *gd);
00190   BOOL Can_Move_Into_Else(GOTO_DESCRIPTOR *gd);
00191   BOOL Goto_Is_Noop(GOTO_DESCRIPTOR *gd) const;
00192   INT Find_Level(WN *wn);
00193   WN *Find_Common_Ancestor(WN *wn1, WN *wn2);
00194   void Dismantle(WN *bad, WN *parent);
00195   enum {MAX_GOTO_EXPANDING_TRANSFORMATIONS = 20 };
00196 };
00197 
00198 class GOTO_WN_PARENT {
00199 public:
00200     WN *wn;
00201     WN *parent;
00202     GOTO_WN_PARENT(WN *w, WN *p) { wn = w; parent = p;}
00203 };
00204 
00205 #endif  // opt_goto_INCLUDED
00206 
00207 
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines