Warning: Attempt to read property "date" on null in /usr/local/www/websvn.planix.org/blame.php on line 247

Warning: Attempt to read property "msg" on null in /usr/local/www/websvn.planix.org/blame.php on line 247
WebSVN – tendra.SVN – Blame – /branches/tendra4/src/installers/power/common/parameter.c – Rev 2

Subversion Repositories tendra.SVN

Rev

Go to most recent revision | Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 7u83 1
/*
2
    Copyright (c) 1993 Open Software Foundation, Inc.
3
 
4
 
5
    All Rights Reserved
6
 
7
 
8
    Permission to use, copy, modify, and distribute this software
9
    and its documentation for any purpose and without fee is hereby
10
    granted, provided that the above copyright notice appears in all
11
    copies and that both the copyright notice and this permission
12
    notice appear in supporting documentation.
13
 
14
 
15
    OSF DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING
16
    ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
17
    PARTICULAR PURPOSE.
18
 
19
 
20
    IN NO EVENT SHALL OSF BE LIABLE FOR ANY SPECIAL, INDIRECT, OR
21
    CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
22
    LOSS OF USE, DATA OR PROFITS, WHETHER IN ACTION OF CONTRACT,
23
    NEGLIGENCE, OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
24
    WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
25
*/
26
 
27
/*
28
    		 Crown Copyright (c) 1997
29
 
30
    This TenDRA(r) Computer Program is subject to Copyright
31
    owned by the United Kingdom Secretary of State for Defence
32
    acting through the Defence Evaluation and Research Agency
33
    (DERA).  It is made available to Recipients with a
34
    royalty-free licence for its use, reproduction, transfer
35
    to other parties and amendment for any purpose not excluding
36
    product development provided that any such use et cetera
37
    shall be deemed to be acceptance of the following conditions:-
38
 
39
        (1) Its Recipients shall ensure that this Notice is
40
        reproduced upon any copies or amended versions of it;
41
 
42
        (2) Any amended version of it shall be clearly marked to
43
        show both the nature of and the organisation responsible
44
        for the relevant amendment or amendments;
45
 
46
        (3) Its onward transfer from a recipient to another
47
        party shall be deemed to be that party's acceptance of
48
        these conditions;
49
 
50
        (4) DERA gives no warranty or assurance as to its
51
        quality or suitability for any purpose and DERA accepts
52
        no liability whatsoever in relation to any use to which
53
        it may be put.
54
*/
55
 
56
 
57
 
58
/**********************************************************************
59
$Author: release $
60
$Date: 1998/02/04 15:49:02 $
61
$Revision: 1.2 $
62
$Log: parameter.c,v $
63
 * Revision 1.2  1998/02/04  15:49:02  release
64
 * Added OSF copyright message.
65
 *
66
 * Revision 1.1.1.1  1998/01/17  15:55:57  release
67
 * First version to be checked into rolling release.
68
 *
69
 * Revision 1.2  1996/10/04  16:03:18  pwe
70
 * add banners and mod for PWE ownership
71
 *
72
**********************************************************************/
73
 
74
 
75
#include "config.h"
76
#include "memtdf.h"
77
#include "codegen.h"
78
#include "geninst.h"
79
#include "translat.h"
80
#include "makecode.h"
81
#include "machine.h"
82
#include "flags.h"
83
#include "myassert.h"
84
#include "comment.h"
85
#include "proc.h"
86
#include "stack.h"
87
#include "mem_copy.h"
88
#include "xalloc.h"
89
#include "parameter.h"
90
bool suspected_varargs = 0;
91
int saved_varargs_register=0;
92
int saved_varargs_offset = 0;
93
 
94
typedef struct
95
{
96
  exp par;
97
  int dest;
98
  int copied;
99
} TREG;
100
 
101
static int spare_fixed;/* The spare t-reg used in case of looping copy i.e if 3-->4 and 4-->3
102
			  replace with 3-->spare_fixed 4-->3 spare_fixed-->4  */
103
static int spare_float;
104
 
105
static int copying_fixed;
106
static int copying_float;
107
bool remember;
108
long fixedfree;
109
long floatfree;
110
 
111
 
112
TREG fixed_array[13];
113
TREG float_array[14];
114
 
115
static void do_fixed_params PROTO_S ((void));
116
static void do_float_params PROTO_S ((void));
117
static void copy_fixed PROTO_S ((int));
118
static void copy_float PROTO_S ((int));
119
static void clear_fixed PROTO_S ((void));
120
static void clear_float PROTO_S ((void));
121
static void set_fixed PROTO_S ((exp,int,int));
122
static void set_float PROTO_S ((exp,int,int));
123
static int getspare PROTO_S ((long));
124
void track_fixed PROTO_S ((int,exp));
125
void track_float PROTO_S ((int,exp));
126
static int end_param;
127
 
128
void output_parameters PROTO_N ((e)) PROTO_T (exp e)
129
{
130
  exp par;
131
 
132
  if (name(e)==general_proc_tag)
133
  {
134
    end_param = GENERAL_PROC_PARAM_REGS + R_FIRST_PARAM - 1;
135
  }
136
  else
137
  {
138
    end_param = PROC_PARAM_REGS + R_FIRST_PARAM - 1;
139
  }
140
 
141
  /* Outputs the code for the parameters */
142
  fixedfree = PROC_TREGS;
143
  floatfree = PROC_FLT_TREGS;
144
  clear_fixed();
145
  clear_float();
146
 
147
  par = son(e);
148
 
149
  for(;;)
150
  {
151
    int param_reg;
152
    exp init_exp;
153
    int param_size;
154
    int param_align;
155
    int param_offset;
156
    bool is_float ;
157
    bool src_in_reg;
158
    bool dest_in_reg;
159
    baseoff stackpos;
160
    where dest;
161
 
162
    if ((!isparam(par)) ||
163
	(name(par)!=ident_tag) ||
164
	(name(son(par))==formal_callee_tag))
165
      break;
166
 
167
    init_exp = son(par);
168
    is_float = is_floating(name(sh(init_exp)));
169
    param_reg = props(init_exp);
170
    param_size = shape_size(sh(init_exp));
171
    param_align = shape_align(sh(init_exp));
172
    param_offset = no(init_exp)>>3;
173
    src_in_reg = param_reg !=0;
174
    dest_in_reg = (props(par) & inanyreg)!=0;
175
 
176
 
177
    if (src_in_reg==1)
178
    {
179
      if(is_float)
180
      {
181
	p_float_params++;
182
      }
183
      else
184
      {
185
	p_fixed_params++;
186
      }
187
    }
188
 
189
    stackpos=boff_location(ENCODE_FOR_BOFF(param_offset,INPUT_CALLER_PARAMETER));    
190
 
191
 
192
    clearvarargparam(par);
193
 
194
    if (dest_in_reg==0 
195
	&& !p_has_no_vcallers 
196
	&& isvis(par)
197
	&& props(init_exp)!=0 
198
	&& last_caller_param(par))
199
    {
200
      /* VARARGS */
201
      int last_size;
202
      int pr;
203
      baseoff v;
204
      v = stackpos;
205
 
206
      setvarargparam(par);
207
 
208
      if (param_size == 0)
209
      {
210
	/* void from <varargs.h> */
211
	param_size = 32;
212
	param_align = 32;
213
      }
214
 
215
      last_size = param_size;
216
      pr = R_FIRST_PARAM + ALIGNNEXT(no(init_exp) + last_size, 32) / 32;
217
 
218
      v.offset += ALIGNNEXT(last_size, 32) / 8;
219
      /* now word align to allow for non word aligned last param */
220
      v.offset &= ~3;
221
      suspected_varargs = 1;
222
      saved_varargs_offset = v.offset;
223
      saved_varargs_register = pr;
224
      while (pr <= end_param)
225
      {
226
	st_ro_ins(i_st, pr, v);comment("varargs save all param regs");
227
	pr++;
228
	v.offset += 4;
229
      }
230
    }    
231
    /* Set up dest */
232
    if (dest_in_reg==1)
233
    {
234
      setregalt(dest.answhere,no(par));
235
    }
236
    else
237
    {
238
      instore is;
239
      is.b = stackpos;
240
      is.adval = 1;
241
      setinsalt(dest.answhere,is);
242
    }
243
    dest.ashwhere.ashsize  = param_size;
244
    dest.ashwhere.ashalign = param_align;
245
 
246
 
247
    /* Work out how the parameter is passed and where it will live */
248
    if (src_in_reg==0 && dest_in_reg==1) 
249
    {
250
      /* STACK  --->  REGISTER */
251
      /* Use move for consistency */
252
      ans a;
253
      instore is;
254
      is.b = stackpos;
255
      is.adval = 0;
256
      setinsalt(a,is);
257
      move(a, dest, PROC_TREGS | PARAM_TREGS, is_signed(sh(init_exp)));
258
    }
259
    else if (src_in_reg==1 && dest_in_reg ==0)
260
    {
261
      /* REGISTER  --->  STACK */
262
      bool is_aggregate =IS_AGGREGATE(sh(init_exp));
263
      if (is_aggregate)
264
      {
265
	/* Whole or part of struct passed in param t-regs */
266
	int last_st_reg;
267
	int r;
268
 
269
	last_st_reg = param_reg + (ALIGNNEXT(param_size, 32)/32) - 1;
270
	if (last_st_reg > end_param)
271
	{
272
	  last_st_reg = end_param;
273
	}
274
	for (r = param_reg; r <= last_st_reg; r++)
275
	{
276
	  st_ro_ins(i_st, r, stackpos);comment("copy param struct onto stack");
277
	  stackpos.offset += 4;
278
	}
279
	p_fixed_params +=(last_st_reg - param_reg);
280
      }
281
      else
282
      {
283
	ans a;
284
	freg fr;
285
 
286
	if(is_float)
287
	{
288
	  fr.dble = is_double_precision((sh(init_exp)));
289
	  fr.fr = param_reg;
290
	  setfregalt(a,fr);
291
	}
292
	else
293
	{
294
	  setregalt( a, param_reg);
295
	}
296
	move(a,dest,PROC_TREGS|PARAM_TREGS,0);
297
      }
298
    }
299
    else if(src_in_reg==1 && dest_in_reg==1)
300
    {
301
      /* REGISTER  --->  REGISTER */
302
      int dest_reg = no(par);
303
      ASSERT(dest_reg!=0);/* This is now set up in needscan*/
304
      if ((props(par) & inreg_bits)!=0)
305
      {
306
	if (IS_SREG(dest_reg))
307
	{
308
	  /* FIXED REGISTER --> FIXED S-REG */
309
	  mov_rr_ins(param_reg , dest_reg);comment("copy param into an s-reg");
310
	  track_fixed(param_reg,par);
311
	}
312
	else
313
	{
314
	  /* FIXED REGISTER --> FIXED T-REG */
315
	  set_fixed(par,param_reg ,  dest_reg);
316
	}
317
      }
318
      else
319
      {
320
	if (IS_FLT_SREG(dest_reg))
321
	{
322
	  /* FLOAT REGISTER --> FLOAT S-REG */
323
	  rrf_ins(i_fmr,param_reg , dest_reg );
324
	  track_float(param_reg,par);
325
	}
326
	else
327
	{
328
	  /* FLOAT REGISTER --> FLOAT T-REG */
329
	  set_float(par,param_reg , dest_reg);
330
	}
331
      }
332
    }
333
    else
334
    {
335
      /* LIVES IN PLACE ON STACK */
336
    }
337
 
338
    par = bro(son(par));
339
  }
340
  do_fixed_params();
341
  do_float_params();
342
  return;
343
}
344
 
345
 
346
static void do_fixed_params PROTO_Z ()
347
{
348
  int r;
349
 
350
  spare_fixed = getspare(fixedfree) ;
351
  copying_fixed = spare_fixed;
352
  copy_fixed(spare_fixed);
353
 
354
  for(r=R_FIRST_PARAM;r<=end_param;r++)
355
  {
356
    remember = 0;
357
    copying_fixed = r;
358
    copy_fixed(r);
359
    if (remember==1)
360
    {
361
      mov_rr_ins( spare_fixed , copying_fixed );comment("move param to its new reg");
362
      track_fixed( spare_fixed , fixed_array[copying_fixed].par);
363
    }
364
  }
365
  return;
366
}  
367
static void do_float_params PROTO_Z ()
368
{
369
  int r;
370
 
371
  spare_float = getspare(floatfree);
372
  copying_float = spare_float;
373
  copy_float(spare_float);
374
 
375
  for(r=FR_FIRST_PARAM;r<=FR_LAST_PARAM;r++)
376
  {
377
    remember = 0;
378
    copying_float = r;
379
    copy_float(r);
380
    if (remember==1)
381
    {
382
      rrf_ins(i_fmr,spare_float,copying_float);
383
      track_float(spare_float,float_array[copying_float].par);
384
    }
385
  }
386
  return;
387
} 
388
static void copy_fixed PROTO_N ((reg)) PROTO_T (int reg)
389
{
390
  if(fixed_array[reg].copied==1)
391
  {
392
    return;
393
  }
394
  if(fixed_array[reg].dest==reg)
395
  {
396
    fixed_array[reg].copied=1;
397
    return;
398
  }
399
  if(fixed_array[reg].dest==copying_fixed)
400
  {
401
    /* We have gone round in a loop */
402
    remember = 1;
403
    mov_rr_ins(reg,spare_fixed);comment("copy param reg to new location");
404
    fixed_array[reg].copied=1;
405
    return;
406
  }
407
  copy_fixed(fixed_array[reg].dest);
408
  mov_rr_ins(reg,fixed_array[reg].dest);comment("copy param reg to new reg");
409
  track_fixed(reg,fixed_array[reg].par);
410
  fixed_array[reg].copied=1;
411
  return;
412
}
413
static void copy_float PROTO_N ((reg)) PROTO_T (int reg)
414
{
415
  if(float_array[reg].copied==1)
416
  {
417
    return;
418
  }
419
  if(float_array[reg].dest==reg)
420
  {
421
    float_array[reg].copied=1;
422
    return;
423
  }
424
  if(float_array[reg].dest==copying_float)
425
  {
426
    /* We have gone round in a loop */
427
    remember = 1;
428
    rrf_ins(i_fmr,reg,spare_float);
429
    float_array[reg].copied=1;
430
    return;
431
  }
432
  copy_float(float_array[reg].dest);
433
  rrf_ins(i_fmr,reg,float_array[reg].dest);
434
  track_float(reg,float_array[reg].par);
435
  float_array[reg].copied=1;
436
  return;
437
} 
438
 
439
 
440
 
441
static void clear_fixed PROTO_Z ()
442
{
443
  int r;
444
  for(r=0;r<=12;r++)
445
  {
446
    fixed_array[r].par = nilexp;
447
    fixed_array[r].dest = 0;
448
    fixed_array[r].copied = 1;
449
  }
450
  return;
451
}
452
static void clear_float PROTO_Z ()
453
{
454
  int r;
455
  for (r=0;r<=13;r++)
456
  {
457
    float_array[r].par = nilexp;
458
    float_array[r].dest = 0;
459
    float_array[r].copied = 1;
460
  }
461
  return;
462
}
463
 
464
static void set_fixed PROTO_N ((p,from,to)) PROTO_T (exp p X int from X int to )
465
{
466
  ASSERT(IS_PARAM_REG(from));
467
  ASSERT(IS_TREG(to));
468
  ASSERT(to!=R_TMP0);
469
  fixed_array[from].par = p;
470
  fixed_array[from].dest = to;
471
  fixed_array[from].copied = 0;
472
  fixedfree |= RMASK(to);
473
}
474
static void set_float PROTO_N ((p,from,to)) PROTO_T (exp p X int from X int to )
475
{
476
  ASSERT(IS_FLT_PARAM_REG(from));
477
  ASSERT(IS_FLT_TREG(to));
478
  float_array[from].par = p;
479
  float_array[from].dest = to;
480
  float_array[from].copied = 0;
481
  floatfree |= RMASK(to);
482
}
483
static int getspare PROTO_N ((s)) PROTO_T (long s)
484
{
485
  int r;
486
  for(r=0;r<=31;r++)
487
  {
488
    if ((s & RMASK(r))==0)
489
    {
490
      return r;
491
    }
492
  }
493
  fail("getspare failed");
494
  return 100;
495
}
496
 
497
void track_fixed PROTO_N ((reg,id)) PROTO_T (int reg X exp id)
498
{
499
  exp def = son(id);
500
 
501
  if(pt(id)!=nilexp && keep_eq_size(sh(def),sh(pt(id))))
502
  {
503
    if(isvar(id))
504
    {
505
      keepcont(pt(id),reg);
506
    } 
507
    else
508
    {
509
      keepreg(pt(id),reg);
510
    }
511
  }
512
  return;
513
}
514
 
515
void track_float PROTO_N ((reg,id)) PROTO_T (int reg X exp id)
516
{
517
  return;
518
}