Subversion Repositories tendra.SVN

Rev

Rev 2 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 7u83 1
/*
2
    		 Crown Copyright (c) 1997
3
 
4
    This TenDRA(r) Computer Program is subject to Copyright
5
    owned by the United Kingdom Secretary of State for Defence
6
    acting through the Defence Evaluation and Research Agency
7
    (DERA).  It is made available to Recipients with a
8
    royalty-free licence for its use, reproduction, transfer
9
    to other parties and amendment for any purpose not excluding
10
    product development provided that any such use et cetera
11
    shall be deemed to be acceptance of the following conditions:-
12
 
13
        (1) Its Recipients shall ensure that this Notice is
14
        reproduced upon any copies or amended versions of it;
15
 
16
        (2) Any amended version of it shall be clearly marked to
17
        show both the nature of and the organisation responsible
18
        for the relevant amendment or amendments;
19
 
20
        (3) Its onward transfer from a recipient to another
21
        party shall be deemed to be that party's acceptance of
22
        these conditions;
23
 
24
        (4) DERA gives no warranty or assurance as to its
25
        quality or suitability for any purpose and DERA accepts
26
        no liability whatsoever in relation to any use to which
27
        it may be put.
28
*/
29
 
30
 
31
/* 	frames.c,v 1.5 1995/09/29 09:45:02 john Exp	 */
32
 
33
#ifndef lint
34
static char vcid[] = "frames.c,v 1.5 1995/09/29 09:45:02 john Exp";
35
#endif /* lint */
36
#include "config.h"
37
#include "common_types.h"
38
#include "frames.h"
39
#include "procrecs.h"
40
#include "expmacs.h"
41
#include "tags.h"
42
#include "bitsmacs.h"
43
#include "reg_defs.h"
44
#include "fail.h"
45
#include "cross.h"
46
#include "bool.h"
47
extern int bitsin PROTO_S ((int32));
48
extern exp father PROTO_S ((exp));
49
 
50
bool Has_fp = FALSE;
51
bool Has_tos = FALSE;
52
bool No_S = FALSE;
53
bool Has_vcallees = FALSE;
54
bool Has_no_vcallers = TRUE;
55
 
56
int local_reg = 14;
57
int callee_size;
58
 
59
#define max(x,y)	(x>y)?x:y
60
 
61
#define min(x,y)        (x>y)?y:x
62
 
63
void setframe_flags
64
    PROTO_N ( ( e,leaf ) )
65
    PROTO_T ( exp e X bool leaf )
66
{
67
   /* e is proc_tag */
68
  No_S = (!leaf && (name(e) != general_proc_tag || !proc_has_nolongj(e))
69
	  && proc_uses_crt_env(e) && proc_has_lv(e));
70
  Has_fp = (No_S || proc_has_alloca(e)|| name(e) == general_proc_tag);
71
  Has_tos = (No_S && proc_has_alloca(e));
72
  Has_vcallees = (name(e) == general_proc_tag && proc_has_vcallees(e));
73
  Has_no_vcallers = (name(e) == proc_tag || !proc_has_vcallers(e));
74
#ifdef Try_No_S
75
  No_S = TRUE;
76
#endif
77
#ifdef Try_Has_fp
78
  Has_fp = !leaf;
79
#endif
80
#ifdef Try_Has_tos
81
  Has_tos = TRUE;
82
#endif      
83
}
84
 
85
/*
86
  sets up the size of the frame, and the positions in which to 
87
  save the registers.
88
*/
89
void setframe_info
90
    PROTO_N ( ( e ) )
91
    PROTO_T ( exp e )
92
{
93
  procrec * pr = & procrecs[no(e)];			 
94
  needs * ndpr = & pr->needsproc;
95
  spacereq *sppr = & pr->spacereqproc;
96
  long pprops = (ndpr->propsneeds);
97
  bool leaf = (pprops & anyproccall) == 0; 
98
  int ma = ndpr->maxargs;	/* maxargs of proc body in bits */	
99
  int pa = ndpr->numparams;
100
  long st = sppr->stack;	/* space for locals in bits */
101
  int nofixdump;
102
  int nofloatdump;
103
  int save_offset;
104
  setframe_flags(e, leaf);
105
 
106
  if(has_c_vararg(e) || !Has_no_vcallers){
107
    pa=12*64;	/* should be 11 */
108
  }
109
  else{
110
    pa=min(pa,6*64);
111
  }
112
 
113
  st = (st + 32) & ~63;
114
  pa = (pa+32)&~63;
115
  ma = (ma + 32) & ~63;	/* put on 64 bit boundaries */
116
  pr->max_args = ma;
117
  save_offset=max(ma-384,0);
118
  /* locate the register to be saved */
119
  pr->fixdump = sppr->fixdump<<9;/* 8 */
120
  if (!leaf ) {
121
    pr->fixdump |= 1 << RA;
122
  }	/* space for return address */
123
  if(No_S) {
124
    pr->fixdump |= (Has_fp)?0x7e00:0xfe00;
125
  }
126
  pr->floatdump = (sppr->fltdump<<1);	/* wrong! */
127
  nofixdump = bitsin (pr->fixdump);
128
  nofloatdump = bitsin (pr->floatdump);
129
  /* no of fixed s-regs to be dumped */
130
  pr->frame_size=pa+st+save_offset+(nofixdump+nofloatdump)*64;
131
  pr->frame_size+=((has_float(e)!=0 || !optop(e))?64:0);
132
  /* reserve an extra quadword for float reg <-> general reg 
133
     transfers */
134
 
135
  if (Has_fp) { 
136
    pr->frame_size +=64; /* extra word for old fp  */
137
/*    pr->callee_size += 128;*/
138
  }
139
 
140
  pr->dumpstart=save_offset>>3;
141
  pr->fldumpstart=pr->dumpstart+8*nofixdump;
142
  pr->locals_offset = (pr->fldumpstart + 8*(nofloatdump+(has_float(e)!=0 ||
143
							 !optop(e))))<<3;
144
 
145
  pr->paramsdumpstart = pr->locals_offset+st + ((Has_fp)?64:0);
146
  return;
147
}	
148
 
149
int frame_offset
150
    PROTO_N ( ( id ) )
151
    PROTO_T ( exp id )
152
{
153
  exp p;
154
  procrec * pr;
155
  int  x = no (id);
156
  int  b = x & 0x3f;
157
 
158
  Assert(name(id) == ident_tag);
159
  for (p = father(id); name(p)!=proc_tag && name(p)!=general_proc_tag; 
160
		       p = father(p));
161
  pr = & procrecs[no(p)];
162
  if((b == SP) || (b == FP)){
163
    return ((x - b) >> 4) + 
164
      ((pr->locals_offset - pr->frame_size - pr->callee_size)>>3);
165
  }	
166
  else if (b == local_reg){
167
    return ((x-b)>>4) + (pr->locals_offset>>3) - (pr->frame_size>>3) 
168
      /*- (pr->callee_size>>3)*/;
169
  }
170
  else{
171
    bool Has_vcallees = (name(p) == general_proc_tag && proc_has_vcallees(p));
172
    int n = -8 - (no(son(id))>>3);
173
    if(isparam(id) && name(son(id)) != formal_callee_tag){
174
      return n;
175
    }	
176
    else if(isparam(id) && name(son(id)) == formal_callee_tag){
177
      return ((Has_vcallees)?n:((pr->callee_size>>3) - n));
178
    }
179
    else{
180
      failer("Illegal frame offset");
181
      return 0;
182
    }
183
  }
184
}
185
 
186
 
187