Pristine Ack-5.5
[Ack-5.5.git] / util / ego / sr / sr_aux.c
1 /* $Id: sr_aux.c,v 1.5 1994/06/24 10:32:04 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 /* S T R E N G T H   R E D U C T I O N
7  *
8  * S R _ A U X . C
9  *
10  */
11
12
13 #include <em_mnem.h>
14 #include <em_pseu.h>
15 #include "../share/types.h"
16 #include "sr.h"
17 #include "../share/debug.h"
18 #include "../share/global.h"
19 #include "../share/lset.h"
20 #include "../share/aux.h"
21 #include "sr_aux.h"
22 #include "sr_xform.h"
23
24 #define INSIDE_LOOP(b,lp)  Lis_elem(b,lp->LP_BLOCKS)
25
26
27 bool is_loopconst(lnp,vars)
28         line_p lnp;
29         lset   vars;
30 {
31         Lindex i;
32
33         assert(TYPE(lnp) == OPSHORT || TYPE(lnp) == OPOFFSET);
34         if (!is_regvar(off_set(lnp))) return FALSE;
35         for (i = Lfirst(vars); i != (Lindex) 0; i = Lnext(i,vars)) {
36                 if (same_local(Lelem(i),lnp)) {
37                         return FALSE; /* variable was changed */
38                 }
39         }
40         return TRUE;
41 }
42
43
44 bool is_caddress(lnp,vars)
45         line_p lnp;
46         lset   vars;  /* variables changed in loop */
47 {
48         /* See if lnp is a single instruction (i.e. without arguments)
49          * that pushes a loop-invariant entity of size pointer-size (ps)
50          * on the stack.
51          */
52
53         if (lnp == (line_p) 0) return FALSE;
54         switch(INSTR(lnp)) {
55                 case op_lae:
56                 case op_lal:
57                         return TRUE;
58                 case op_lol:
59                         return ps == ws && is_loopconst(lnp,vars);
60                 case op_ldl:
61                         return ps == 2*ws && is_loopconst(lnp,vars);
62                 default:
63                         return FALSE;
64         }
65         /* NOTREACHED */
66 }
67
68
69
70 STATIC arg_p find_arg(n,list)
71         int n;
72         arg_p list;
73 {
74         /* Find the n-th element of the list */
75
76         while (--n) {
77                 if (list == (arg_p) 0) break;
78                 list = list->a_next;
79         }
80         return list;
81 }
82
83
84 int elemsize(lnp)
85         line_p lnp;
86 {
87         /* lnp is an instruction that loads the address of an array
88          * descriptor. Find the size of the elements of the array.
89          * If this size cannot be determined (e.g. the descriptor may
90          * not be in a rom) then return UNKNOWN_SIZE.
91          */
92
93         dblock_p d;
94         arg_p v;
95
96         assert (lnp != (line_p) 0);
97         if (INSTR(lnp) == op_lae) {
98                 d = OBJ(lnp)->o_dblock; /* datablock */
99                 if (d->d_pseudo == DROM  &&
100                     (v = find_arg(3,d->d_values)) != (arg_p) 0 &&
101                     v->a_type == ARGOFF) {
102                         return (int) v->a_a.a_offset;
103                 }
104         }
105         return UNKNOWN_SIZE;
106 }
107
108
109
110 concatenate(list1,list2)
111         line_p list1,list2;
112 {
113         /* Append list2 to the end of list1. list1 may not be empty. */
114
115         register line_p l;
116
117         assert(list1 != (line_p) 0);
118         for (l =list1; l->l_next != (line_p) 0; l = l->l_next);
119         l->l_next = list2;
120 }