Pristine Ack-5.5
[Ack-5.5.git] / util / ego / il / il.h
1 /* $Id: il.h,v 1.6 1994/06/24 10:25:15 ceriel Exp $ */
2 /*
3  * (c) copyright 1987 by the Vrije Universiteit, Amsterdam, The Netherlands.
4  * See the copyright notice in the ACK home directory, in the file "Copyright".
5  */
6 /* I N T E R N A L   D A T A S T R U C T U R E S   O F 
7  *
8  *           I N L I N E   S U B S T I T U T I O N   
9  *
10  */
11
12
13 typedef struct actual   *actual_p;
14 typedef struct calcnt   *calcnt_p;
15 typedef short call_id;
16
17 struct call {
18         proc_p   cl_caller;     /* calling procedure                    */
19         call_id  cl_id;         /* uniquely denotes a CAL instruction   */
20         proc_p   cl_proc;       /* the called procedure                 */
21         byte     cl_looplevel;  /* loop nesting level of the CAL        */
22         bool     cl_flags;      /* flag bits                            */
23         short    cl_ratio;      /* indicates 'speed gain / size lost'   */
24         call_p   cl_cdr;        /* link to next call                    */
25         call_p   cl_car;        /* link to nested calls                 */
26         actual_p cl_actuals;    /* actual parameter expr. trees         */
27 };
28
29 #define CLF_INLPARS 017         /* min(15,nr. of inline parameters) */
30 #define CLF_SELECTED    020     /* is call selected for expansion? */
31 #define CLF_EVER_EXPANDED 040   /* ever expanded? e.g. in a nested call.  */
32 #define CLF_FIRM        0100    /* indicates if the call takes place in a
33                                  * firm block of a loop (i.e. one that
34                                  * is always executed, except
35                                  * -perhaps- at the last iteration).
36                                  * Used for heuristics only.
37                                  */
38
39 struct actual {
40         line_p   ac_exp;        /* copy of EM text                      */
41                                 /* 0 for actuals that are not inline    */
42         offset   ac_size;       /* number of bytes of parameter         */
43         bool     ac_inl;        /* TRUE if it may be expanded in line   */
44         actual_p ac_next;       /* link                                 */
45 };
46
47
48 struct formal {
49         offset   f_offset;      /* offsetin bytes                       */
50         byte     f_flags;       /* flags FF_BAD etc.                    */
51         byte     f_type;        /* SINGLE, DOUBLE,POINTER,UNKNOWN       */
52         formal_p f_next;        /* link                                 */
53 };
54
55
56 /* flags of formal: */
57
58 #define FF_BAD          01
59 #define FF_REG          02
60 #define FF_ONCEUSED     04
61 #define FF_OFTENUSED    06
62 #define USEMASK         014
63
64 /* types of formals: */
65
66 #define SINGLE          1
67 #define DOUBLE          2
68 #define POINTER         3
69 #define UNKNOWN         4
70
71 /* 'call-count' information keeps track of the number
72  * of times one procedure calls another. Conceptually,
73  * it may be regarded as a two dimensional array, where
74  * calcnt[p,q] is the number of times p calls q. As this
75  * matrix would be very dense, we use a more efficient
76  * list representation. Every procedure has a list
77  * of calcnt structs.
78  */
79
80 struct calcnt {
81         proc_p  cc_proc;        /* the called procedure */
82         short   cc_count;       /* # times proc. is called in the
83                                  * original text of the caller.
84                                  */
85         calcnt_p cc_next;       /* link                 */
86 };
87
88
89
90
91 extern int complete_program;
92 extern int calnr;
93 extern calcnt_p cchead;         /* calcnt info of current proc */
94
95 /* Macro's for extended data structures */
96
97 #define P_CALS          p_extend->px_il.p_cals
98 #define P_SIZE          p_extend->px_il.p_size
99 #define P_FORMALS       p_extend->px_il.p_formals
100 #define P_NRCALLED      p_extend->px_il.p_nrcalled
101 #define P_CCADDR        p_extend->px_il.p_ccaddr
102 #define P_LADDR         p_extend->px_il.p_laddr
103 #define P_ORGLABELS     p_extend->px_il.p_orglabels
104 #define P_ORGLOCALS     p_extend->px_il.p_orglocals
105
106 /* flags2: */
107
108 #define PF_UNSUITABLE   01
109 #define PF_NO_INLPARS   02
110 #define PF_FALLTHROUGH  04
111 #define PF_DISPENSABLE  010
112 #define PF_CHANGED      020
113
114
115 /* kinds of usages: */
116
117 #define USE     0
118 #define CHANGE  1
119 #define ADDRESS 2
120
121
122
123
124 /* We do not expand calls if:
125  * - the called procedure has to many local variables
126  * - the calling procedure is already very large
127  * - the called procedure is to large.
128  */
129
130 #define MANY_LOCALS(p)  (p->p_localbytes > LOCAL_THRESHOLD)
131 #define LOCAL_THRESHOLD         200
132 #define BIG_CALLER(p)   (p->P_SIZE > CALLER_THRESHOLD)
133 #define CALLER_THRESHOLD        500
134 #define BIG_PROC(p)     (p->P_SIZE > CALLEE_THRESHOLD)
135 #define CALLEE_THRESHOLD        100
136
137 #define FALLTHROUGH(p)  (p->p_flags2 & PF_FALLTHROUGH)
138 #define DISPENSABLE(p)  p->p_flags2 |= PF_DISPENSABLE
139 #define IS_DISPENSABLE(p) (p->p_flags2 & PF_DISPENSABLE)
140 #define SELECTED(c)     c->cl_flags |= CLF_SELECTED
141 #define IS_SELECTED(c)  (c->cl_flags & CLF_SELECTED)
142 #define EVER_EXPANDED(c) c->cl_flags |= CLF_EVER_EXPANDED
143 #define IS_EVER_EXPANDED(c) (c->cl_flags & CLF_EVER_EXPANDED)
144 #define UNSUITABLE(p)   p->p_flags2 |= PF_UNSUITABLE
145 #define SUITABLE(p)     (!(p->p_flags2&PF_UNSUITABLE))
146 #define INLINE_PARS(p)  (!(p->p_flags2&PF_NO_INLPARS))
147 #define PARAMS_UNKNOWN(p) (p->p_nrformals == UNKNOWN_SIZE)
148
149 extern int Ssubst;
150 #ifdef VERBOSE
151 extern int Senv,Srecursive,Slocals,Sinstrlab,Sparsefails,Spremoved,Scals;
152 extern int Sbig_caller,Sdispensable,Schangedcallee,Sbigcallee,Sspace,Szeroratio;
153 #endif
154
155 /* extra core-allocation macros */
156
157 #define newcall()       (call_p) newstruct(call)
158 #define newactual()     (actual_p) newstruct(actual)
159 #define newformal()     (formal_p) newstruct(formal)
160 #define newcalcnt()     (calcnt_p) newstruct(calcnt)
161 #define newilpx()       (pext_p) newstruct(pext_il)
162
163 #define oldcall(x)      oldstruct(call,x)
164 #define oldactual(x)    oldstruct(actual,x)
165 #define oldformal(x)    oldstruct(formal,x)
166 #define oldcalcnt(x)    oldstruct(calcnt,x)
167 #define oldilpx(x)      oldstruct(pext_il,x)