Subversion Repositories tendra.SVN

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
6 7u83 1
/*
2
 * Copyright (c) 2002-2005 The TenDRA Project <http://www.tendra.org/>.
3
 * All rights reserved.
4
 *
5
 * Redistribution and use in source and binary forms, with or without
6
 * modification, are permitted provided that the following conditions are met:
7
 *
8
 * 1. Redistributions of source code must retain the above copyright notice,
9
 *    this list of conditions and the following disclaimer.
10
 * 2. Redistributions in binary form must reproduce the above copyright notice,
11
 *    this list of conditions and the following disclaimer in the documentation
12
 *    and/or other materials provided with the distribution.
13
 * 3. Neither the name of The TenDRA Project nor the names of its contributors
14
 *    may be used to endorse or promote products derived from this software
15
 *    without specific, prior written permission.
16
 *
17
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS
18
 * IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
19
 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
20
 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR
21
 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
22
 * EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
23
 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
24
 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
25
 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
26
 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
27
 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28
 *
29
 * $Id$
30
 */
31
/*
32
    		 Crown Copyright (c) 1997
33
 
34
    This TenDRA(r) Computer Program is subject to Copyright
35
    owned by the United Kingdom Secretary of State for Defence
36
    acting through the Defence Evaluation and Research Agency
37
    (DERA).  It is made available to Recipients with a
38
    royalty-free licence for its use, reproduction, transfer
39
    to other parties and amendment for any purpose not excluding
40
    product development provided that any such use et cetera
41
    shall be deemed to be acceptance of the following conditions:-
42
 
43
        (1) Its Recipients shall ensure that this Notice is
44
        reproduced upon any copies or amended versions of it;
45
 
46
        (2) Any amended version of it shall be clearly marked to
47
        show both the nature of and the organisation responsible
48
        for the relevant amendment or amendments;
49
 
50
        (3) Its onward transfer from a recipient to another
51
        party shall be deemed to be that party's acceptance of
52
        these conditions;
53
 
54
        (4) DERA gives no warranty or assurance as to its
55
        quality or suitability for any purpose and DERA accepts
56
        no liability whatsoever in relation to any use to which
57
        it may be put.
58
*/
59
 
60
 
61
/* freebsd/diag_out.c */
62
 
63
#include "config.h"
64
#include "common_types.h"
65
#include "basicread.h"
66
#include "out.h"
67
#include "machine.h"
68
#include "shapemacs.h"
69
#include "expmacs.h"
70
#include "tags.h"
71
#include "szs_als.h"
72
#include "diagglob.h"
73
#include "xalloc.h"
74
#include "exp.h"
75
#include "mark_scope.h"
76
#include "externs.h"
77
#ifdef NEWDIAGS
78
#include "codermacs.h"
79
#include "instr.h"
80
#endif
81
 
82
 
83
 
84
/*
85
    FORWARD DECLARATIONS
86
*/
87
 
88
static void stab_scope_open(long);
89
static void stab_scope_close(long);
90
static void stab_file(long, bool);
91
static void stab_local(diag_info *, int, exp);
92
static void stab_types(void);
93
 
94
 
95
 
96
 
97
/*
98
    DIAGNOSTICS FILE
99
*/
100
 
101
static FILE *dg_file;
102
static char *dg_file_name;
103
 
104
 
105
/*
106
    BASIC TYPE NUMBERS
107
*/
108
 
109
#define STAB_SCHAR	4
110
#define STAB_UCHAR	6
111
#define STAB_SSHRT	2
112
#define STAB_USHRT	3
113
#define STAB_SLONG	1
114
#define STAB_ULONG	8
115
#define STAB_FLOAT	10
116
#define STAB_DBL	11
117
#define STAB_LDBL	12
118
#define STAB_VOID	13
119
#define STAB_S64	14
120
#define STAB_U64	15
121
#define NO_STABS	16
122
 
123
 
124
/*
125
    80x86 register numbers
126
*/
127
 
128
#ifdef NEWDIAGS
129
static long reg_stabno[8] = {0, 2, 1, 3, 7, 6, 5, 4};
130
#endif
131
 
132
/*
133
    BASIC POINTERS
134
*/
135
 
136
static long stab_ptrs[NO_STABS] = {
137
    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
138
};
139
 
140
 
141
/*
142
    CURRENT TYPE NUMBER
143
*/
144
 
145
static long typeno;
146
 
147
 
148
/*
149
    SIZE OF LAST STAB TYPE OUTPUT
150
*/
151
 
152
static long last_type_sz = 0;
153
 
154
 
155
/*
156
    CURRENT LINE NUMBER AND FILE NUMBER
157
*/
158
 
159
long currentlno = -1;
160
long currentfile = -1;
161
 
162
 
163
/*
164
    ARRAY OF TYPE SIZES
165
*/
166
 
167
static long *type_sizes;
168
static int total_type_sizes = 0;
169
 
170
 
171
/*
172
    SETTING AND GETTING TYPE SIZES
173
*/
174
 
175
#define set_stab_size(i)	type_sizes[(i)] = last_type_sz
176
#define get_stab_size(i)	(type_sizes[(i)])
177
 
178
 
179
/*
180
    GET THE NEXT TYPE NUMBER
181
*/
182
 
183
static long next_typen
184
(void)
185
{
186
    if (typeno >= total_type_sizes) {
187
	int i, n = total_type_sizes, m = n + 100;
188
	type_sizes = (long *)xrealloc((void*)(CH type_sizes),
189
					m * sizeof(long));
190
	for (i = n; i < m; i++)type_sizes[i] = 0;
191
	total_type_sizes = m;
192
    }
193
    return(typeno++);
194
}
195
 
196
 
197
/*
198
    ARRAY OF FILE DESCRIPTORS
199
*/
200
 
201
static filename *fds = NULL;
202
static int szfds = 0;
203
static int nofds = 0;
204
 
205
 
206
/*
207
    ADD A NEW FILE TO THE ARRAY OF FILE DESCRIPTORS
208
*/
209
 
210
void stab_collect_files
211
(filename f)
212
{
213
    if (fds == NULL) {
214
	szfds += 10;
215
	fds = (filename *)xmalloc(szfds * sizeof(filename));
216
    } else if (nofds >= szfds) {
217
	szfds += 10;
218
	fds = (filename *)xrealloc((void*)(CH fds),
219
				szfds * sizeof(filename));
220
    }
221
    fds[nofds++] = f;
222
    return;
223
}
224
 
225
 
226
/*
227
    FIND THE FILE DESCRIPTOR CORRESPONDING TO A FILE NAME
228
*/
229
 
230
static long find_file
231
(char * f)
232
{
233
    long i;
234
    for (i = 0; i < nofds; i++) {
235
	if (strcmp(f, fds[i] ->file.ints.chars) == 0) return(i);
236
    }
237
    return(0);
238
}
239
 
240
 
241
static int last_proc_cname;
242
static char * last_proc_pname;
243
static int in_proc = 0;
244
 
245
static void out_procname
246
(void)
247
{
248
  if (last_proc_cname == -1) {
249
    outs(last_proc_pname);
250
  }
251
  else {
252
    outs(local_prefix);
253
    outn((long)last_proc_cname);
254
  };
255
}
256
 
257
 
258
/*
259
    OUTPUT A FILE POSITION CONSTRUCT
260
*/
261
 
262
#define N_SLINE 0x44
263
#define N_DSLINE 0x46
264
#define N_BSLINE 0x48
265
#define N_LBRAC  0xc0
266
#define N_RBRAC  0xe0
267
 
268
static void stabd
269
(long findex, long lno, int seg)
270
{
271
    long i;
272
 
273
    if (findex == currentfile && lno == currentlno) return;
274
    stab_file(findex, 1);
275
 
276
    if (seg != 0)		/* 0 suppresses always */
277
    {
278
      if (seg < 0 && !freebsd_elf)
279
	seg = - seg;
280
      if (seg > 0)		/* -ve line nos are put out in the stabs */
281
      {
282
	i = next_lab();
283
	fprintf(dg_file, "%sL.%ld:\n", local_prefix, i);
284
	fprintf(dg_file, "\t.stabn\t0x%x,0,%ld,%sL.%ld",seg, lno, local_prefix, i);
285
	if (freebsd_elf && in_proc) {
286
	  outs("-");
287
	  out_procname();
288
	}
289
	outnl();
290
      }
291
    }
292
    currentlno = lno;
293
    return;
294
}
295
 
296
 
297
#ifdef NEWDIAGS
298
/*
299
    OUTPUT DIAGNOSTICS SURROUNDING CODE
300
*/
301
 
302
void code_diag_info
303
(diag_info * d, int proc_no, void(*mcode)(void *), void * args)
304
{
305
  if (d == nildiag) {
306
   (*mcode)(args);
307
    return;
308
  }
309
  switch (d->key) {
310
    case DIAG_INFO_SCOPE: {
311
	stab_scope_open(currentfile);
312
	stabd(currentfile,(long)(currentlno + 1), N_SLINE);
313
	code_diag_info(d->more, proc_no, mcode, args);
314
	stab_scope_close(currentfile);
315
	return;
316
    }
317
    case DIAG_INFO_SOURCE: {
318
	sourcemark *s = &d->data.source.beg;
319
	long f = find_file(s->file->file.ints.chars);
320
	stabd(f,(long)s->line_no.nat_val.small_nat ,N_SLINE);
321
	code_diag_info(d->more, proc_no, mcode, args);
322
	s = &d->data.source.end;
323
	f = find_file(s->file->file.ints.chars);
324
	stabd(f,(long)s->line_no.nat_val.small_nat ,N_SLINE);
325
	return;
326
    }
327
    case DIAG_INFO_ID: {
328
	exp acc = d -> data.id_scope.access;
329
	if (name(acc)!= hold_tag)
330
	  failer("not hold_tag");
331
	acc = son(acc);
332
	if (name(acc) == cont_tag && name(son(acc)) == name_tag && isvar(son(son(acc))))
333
	  acc = son(acc);
334
	if ((name(acc) == name_tag && !isdiscarded(acc) && !isglob(son(acc))) ||
335
		name(acc) == val_tag)
336
	  stab_local(d, proc_no, acc);
337
	code_diag_info(d->more, proc_no, mcode, args);
338
    }
339
  };
340
  return;
341
}
342
 
343
 
344
#else
345
 
346
/*
347
    OUTPUT INITIAL DIAGNOSTICS FOR A DIAGNOSE_TAG
348
*/
349
 
350
void output_diag
351
(diag_info * d, int proc_no, exp e)
352
{
353
  if (d->key == DIAG_INFO_SOURCE) {
354
    sourcemark *s = &d->data.source.beg;
355
    long f = find_file(s->file->file.ints.chars);
356
    stabd(f,(long)s->line_no.nat_val.small_nat ,N_SLINE);
357
    return;
358
  }
359
 
360
  if (d -> key == DIAG_INFO_ID) {
361
    exp acc = d -> data.id_scope.access;
362
 
363
    if (isglob(son(acc)) || no(son(acc)) == 1) return;
364
    mark_scope(e);
365
 
366
    if (props(e) & 0x80) {
367
      stab_scope_open(currentfile);
368
      stabd(currentfile,(long)(currentlno + 1), N_SLINE);
369
    }
370
 
371
    stab_local(d, proc_no, acc);
372
    return;
373
  }
374
}
375
 
376
 
377
/*
378
    OUTPUT FINAL DIAGNOSTICS FOR A DIAGNOSE_TAG
379
*/
380
 
381
void output_end_scope
382
(diag_info * d, exp e)
383
{
384
    if (d->key == DIAG_INFO_SOURCE) {
385
	sourcemark *s = &d->data.source.end;
386
	long f = find_file(s->file->file.ints.chars);
387
	long lno = s->line_no.nat_val.small_nat;
388
	stabd(f, lno, N_SLINE);
389
	return;
390
    }
391
    if (d->key == DIAG_INFO_ID && props(e) & 0x80) {
392
	stab_scope_close(currentfile);
393
	return;
394
    }
395
    return;
396
}
397
 
398
 
399
#endif
400
/*
401
    INITIALISE DIAGNOSTICS
402
*/
403
 
404
void out_diagnose_prelude
405
(void)
406
{
407
    dg_file_name = tmpnam(NULL);
408
    dg_file = fopen(dg_file_name, "w");
409
    if (dg_file == NULL) {
410
	failer("Can't open temporary diagnostics file");
411
	exit(EXIT_FAILURE);
412
    }
413
    stab_types();
414
    return;
415
}
416
 
417
 
418
/*
419
    INITIALIZE DIAGNOSTICS
420
*/
421
 
422
void init_stab_aux
423
(void)
424
{
425
    int c;
426
    FILE *f;
427
    int i, j = -1;
428
    for (i = 0; i < nofds; i++) {
429
	char *s = fds[i] ->file.ints.chars;
430
	int n = (int)strlen(s);
431
	if (n && s[n - 1]!= 'h')j = i;
432
    }
433
    fclose(dg_file);
434
    dg_file = fpout;
435
    if (j >= 0)
436
	fprintf(dg_file, "\t.file\t\"%s\"\n", fds[j] ->file.ints.chars);
437
    else
438
	fprintf(dg_file, "\t.file\t\"no_source_file\"\n");
439
    stab_file((long)j, 0);
440
    f = fopen(dg_file_name, "r");
441
    if (f == NULL) {
442
	failer("Can't open temporary diagnostics file");
443
	exit(EXIT_FAILURE);
444
    }
445
    while (c = fgetc(f), c != EOF)outc(c);
446
    fclose(f);
447
    remove(dg_file_name);
448
    return;
449
}
450
 
451
void out_diagnose_postlude
452
(void)
453
{
454
    long i = next_lab();
455
    fprintf(dg_file, ".text\n");
456
    fprintf(dg_file, "%sL.%ld:\n", local_prefix, i);
457
    fprintf(dg_file, "\t.stabs\t\"\",0x64,0,0,%sL.%ld\n", local_prefix, i);
458
    return;
459
}
460
 
461
 
462
/*
463
    FIND THE STAB OF A SIMPLE SHAPE
464
*/
465
 
466
static long out_sh_type
467
(shape s)
468
{
469
    last_type_sz = shape_size(s);
470
    switch (name(s)) {
471
	case scharhd: return(STAB_SCHAR);
472
	case ucharhd: return(STAB_UCHAR);
473
	case swordhd: return(STAB_SSHRT);
474
	case uwordhd: return(STAB_USHRT);
475
	case slonghd: return(STAB_SLONG);
476
	case ulonghd: return(STAB_ULONG);
477
	case s64hd: return(STAB_S64);
478
	case u64hd: return(STAB_U64);
479
	case shrealhd: return(STAB_FLOAT);
480
	case realhd: return(STAB_DBL);
481
	case doublehd: return(STAB_LDBL);
482
    }
483
    return(STAB_VOID);
484
}
485
 
486
 
487
/*
488
    OUTPUT DIAGNOSTICS DIRECTIVE FOR A FILE
489
*/
490
 
491
static void stab_file
492
(long findex, bool internal)
493
{
494
    static long i = 0;
495
 
496
    if (findex == currentfile || findex < 0 || findex >= szfds) {
497
	return;
498
    }
499
 
500
    if (!internal) {
501
	/* source file */
502
	i = next_lab();
503
	fprintf(dg_file, "%sL.%ld:\n", local_prefix, i);
504
	fprintf(dg_file, "\t.stabs\t\"%s\",0x64,0,0,%sL.%ld\n",
505
		  fds[findex] ->file.ints.chars, local_prefix, i);
506
    } else {
507
	/* included file */
508
	fprintf(dg_file, "\t.stabs\t\"%s\",0x84,0,0,%sL.%ld\n",
509
		  fds[findex] ->file.ints.chars, local_prefix, i);
510
    }
511
    currentfile = findex;
512
    return;
513
}
514
 
515
 
516
/*
517
    ARRAY OF DIAGNOSTIC SCOPES
518
*/
519
 
520
static long open_label = 0;
521
static long bracket_level = 0;
522
 
523
 
524
/*
525
    START OF A DIAGNOSTICS SCOPE
526
*/
527
 
528
static void stab_scope_open
529
(long findex)
530
{
531
    long i;
532
    stab_file(findex, 1);
533
    if (open_label != 0)
534
    {
535
	fprintf(dg_file, "\t.stabn\t0x%x,0,%ld,%sL.%ld\n", N_LBRAC,
536
		  bracket_level, local_prefix, open_label);
537
    }
538
    i = next_lab();
539
    fprintf(dg_file, "%sL.%ld:\n", local_prefix, i);
540
    bracket_level++;
541
    open_label = i;
542
    return;
543
}
544
 
545
 
546
/*
547
    END OF A DIAGNOSTICS SCOPE
548
*/
549
 
550
static void stab_scope_close
551
(long findex)
552
{
553
    long i;
554
    if (open_label != 0)
555
    {
556
	fprintf(dg_file, "\t.stabn\t0x%x,0,%ld,%sL.%ld\n", N_LBRAC,
557
		  bracket_level, local_prefix, open_label);
558
	open_label = 0;
559
    }
560
    i = next_lab();
561
    fprintf(dg_file, "%sL.%ld:\n", local_prefix, i);
562
    fprintf(dg_file, "\t.stabn\t0x%x,0,%ld,%sL.%ld\n", N_RBRAC,
563
		  bracket_level, local_prefix, i);
564
    bracket_level--;
565
    return;
566
}
567
 
568
 
569
/*
570
    DEPTH COUNT FOR STAB TYPES
571
*/
572
 
573
static int max_depth = 64;
574
static int depth_now = 0;
575
 
576
 
577
/*
578
    OUTPUT A DIAGNOSTICS TYPE
579
*/
580
 
581
#define OUT_DT_SHAPE(dt)	out_dt_shape((depth_now = 0, dt))
582
 
583
static void out_dt_shape
584
(diag_type dt)
585
{
586
    if (dt->been_outed) {
587
	fprintf(dg_file, "%d",(int)dt->been_outed);
588
	last_type_sz = get_stab_size(dt->been_outed);
589
	return;
590
    }
591
 
592
    /* SunOS as(1) rejects stab lines >2k so reduce size arbitrarily */
593
    if (depth_now >= max_depth) {
594
	fprintf(dg_file, "%d", STAB_SLONG);
595
	return;
596
    }
597
    depth_now++;
598
 
599
    switch (dt->key) {
600
 
601
	case DIAG_TYPE_PTR: {
602
	    long non;
603
	    diag_type pdt = dt->data.ptr.object;
604
	    if (pdt->key == DIAG_TYPE_VARIETY) {
605
		long pn = out_sh_type(f_integer(pdt->data.var));
606
		non = stab_ptrs[pn];
607
		if (non == 0) {
608
		    non = next_typen();
609
		    stab_ptrs[pn] = non;
610
		    fprintf(dg_file, "%ld=*%ld", non, pn);
611
		} else {
612
		    fprintf(dg_file, "%ld", non);
613
		}
614
	    } else {
615
		non = next_typen();
616
		fprintf(dg_file, "%ld=*", non);
617
		out_dt_shape(dt->data.ptr.object);
618
	    }
619
	    dt->been_outed = non;
620
	    last_type_sz = 32;
621
	    set_stab_size(non);
622
	    break;
623
	}
624
 
625
	case DIAG_TYPE_ARRAY: {
626
#if 0
627
	    long str = no(dt->data.array.stride);
628
#endif
629
	    long lwb = no(dt->data.array.lower_b);
630
	    long upb = no(dt->data.array.upper_b);
631
	    diag_type index_type = dt->data.array.index_type;
632
	    diag_type element_type = dt->data.array.element_type;
633
	    long non = next_typen();
634
	    dt->been_outed = non;
635
	    fprintf(dg_file, "%ld=ar", non);
636
	    out_dt_shape(index_type);
637
	    fprintf(dg_file, ";%ld;%ld;", lwb, upb);
638
	    out_dt_shape(element_type);
639
	    last_type_sz *= (upb - lwb + 1);
640
	    set_stab_size(non);
641
	    break;
642
	}
643
 
644
	case DIAG_TYPE_STRUCT:
645
	case DIAG_TYPE_UNION: {
646
	    int i;
647
	    char su;
648
	    shape s;
649
	    diag_field_list fields;
650
	    long non = next_typen();
651
	    dt->been_outed = non;
652
 
653
	    if (dt->key == DIAG_TYPE_STRUCT) {
654
		fields = dt->data.t_struct.fields;
655
		s = dt->data.t_struct.tdf_shape;
656
		su = 's';
657
	    } else {
658
		fields = dt->data.t_union.fields;
659
		s = dt->data.t_union.tdf_shape;
660
		su = 'u';
661
	    }
662
	    fprintf(dg_file, "%ld=%c%d", non, su, shape_size(s) / 8);
663
 
664
	    for (i = fields->lastused - 1; i >= 0; i--) {
665
		diag_field sf = (fields->array)[i];
666
		long offset = no(sf->where);
667
 
668
		if (depth_now >= max_depth) return;
669
		depth_now++;
670
		fprintf(dg_file, "%s:", sf->field_name.ints.chars);
671
		out_dt_shape(sf->field_type);
672
		fprintf(dg_file, ",%ld,%ld;", offset, last_type_sz);
673
	    }
674
	    fprintf(dg_file, ";");
675
	    last_type_sz = shape_size(s);
676
	    set_stab_size(non);
677
	    break;
678
	}
679
 
680
	case DIAG_TYPE_VARIETY: {
681
	    dt->been_outed = out_sh_type(f_integer(dt->data.var));
682
	    fprintf(dg_file, "%ld", dt->been_outed);
683
	    break;
684
	}
685
 
686
	case DIAG_TYPE_PROC: {
687
	    diag_type result_type = dt->data.proc.result_type;
688
	    long non1 = next_typen();
689
	    long non2 = next_typen();
690
	    dt->been_outed = non1;
691
	    fprintf(dg_file, "%ld=*%ld=f", non1, non2);
692
	    out_dt_shape(result_type);
693
	    last_type_sz = 32;
694
	    set_stab_size(non1);
695
	    set_stab_size(non2);
696
	    break;
697
	}
698
 
699
	case DIAG_TYPE_LOC: {
700
	    /* +++ use qualifier which gives "const"/"volatile" */
701
	    out_dt_shape(dt->data.loc.object);
702
	    break;
703
	}
704
 
705
	case DIAG_TYPE_FLOAT: {
706
	    dt->been_outed = out_sh_type(f_floating(dt->data.f_var));
707
	    fprintf(dg_file, "%ld", dt->been_outed);
708
	    break;
709
	}
710
 
711
	case DIAG_TYPE_NULL: {
712
	    fprintf(dg_file, "%d", STAB_VOID);
713
	    last_type_sz = 0;
714
	    break;
715
	}
716
 
717
	case DIAG_TYPE_BITFIELD: {
718
	    long sz = dt->data.bitfield.no_of_bits.nat_val.small_nat;
719
	    fprintf(dg_file, "%d", STAB_SLONG);
720
	    last_type_sz = sz;
721
	    break;
722
	}
723
 
724
	case DIAG_TYPE_ENUM: {
725
	    int i;
726
	    enum_values_list enumvals = dt->data.t_enum.values;
727
	    long non = next_typen();
728
	    dt->been_outed = non;
729
	    fprintf(dg_file, "%ld=e", non);
730
	    for (i = enumvals->lastused - 1; i >= 0; i--) {
731
		enum_values ef = (enumvals->array)[i];
732
		fprintf(dg_file, "%s:%d,", ef->nme.ints.chars, no(ef->val));
733
	    }
734
	    fprintf(dg_file, ";");
735
	    last_type_sz = 32;
736
	    set_stab_size(non);
737
	    break;
738
	}
739
 
740
	default : {
741
	    fprintf(dg_file, "%d", STAB_VOID);
742
	    last_type_sz = 0;
743
	    break;
744
	}
745
    }
746
    return;
747
}
748
 
749
 
750
/*
751
    OUTPUT DIAGNOSTICS FOR A GLOBAL VARIABLE
752
*/
753
 
754
void diag_val_begin
755
(diag_global * d, int global, int cname, char * pname)
756
{
757
  stabd(find_file(d->data.id.whence.file->file.ints.chars),
758
	(long)d->data.id.whence.line_no.nat_val.small_nat
759
	 , -N_DSLINE);
760
 
761
  fprintf(dg_file, "\t.stabs\t\"%s:%c",
762
	d->data.id.nme.ints.chars,(global ? 'G' : 'S'));
763
  OUT_DT_SHAPE(d->data.id.new_type);
764
  if (global)
765
    fprintf(dg_file, "\",0x20,0,%d,0\n",
766
	d->data.id.whence.line_no.nat_val.small_nat);
767
  else {
768
    fprintf(dg_file, "\",0x28,0,%d,",
769
	d->data.id.whence.line_no.nat_val.small_nat);
770
    if (cname == -1) {
771
      outs(pname);
772
    }
773
    else {
774
      outs(local_prefix);
775
      outn((long)cname);
776
    };
777
    outnl();
778
  };
779
  return;
780
}
781
 
782
void diag_val_end
783
(diag_global * d)
784
{
785
  UNUSED(d);
786
  return;
787
}
788
 
789
 
790
/*
791
    OUTPUT DIAGNOSTICS FOR A PROCEDURE
792
*/
793
 
794
void diag_proc_begin
795
(diag_global * d, int global, int cname, char * pname)
796
{
797
  last_proc_pname = pname;
798
  last_proc_cname = cname;
799
  in_proc = 1;
800
  if (!d)
801
    return;
802
 
803
  stabd(find_file(d->data.id.whence.file->file.ints.chars),
804
	(long)d->data.id.whence.line_no.nat_val.small_nat
805
	 ,0);
806
 
807
  outs("\t.stabs\t\"");
808
  outs(d->data.id.nme.ints.chars);
809
  if (global)
810
    outs(":F");
811
  else
812
    outs(":f");
813
  OUT_DT_SHAPE(d->data.id.new_type->data.proc.result_type);
814
  outs("\",0x24,0,0,");
815
  out_procname();
816
  outnl();
817
  return;
818
}
819
 
820
void diag_proc_end
821
(diag_global * d)
822
{
823
  UNUSED(d);
824
  in_proc = 0;
825
  return;
826
}
827
 
828
 
829
 
830
/*
831
    OUTPUT DIAGNOSTICS FOR A LOCAL VARIABLE
832
*/
833
 
834
static void stab_local
835
(diag_info * d, int proc_no, exp acc)
836
{
837
  int p, param_dec;
838
#ifdef NEWDIAGS
839
  long acc_type;
840
  if (name(acc) == name_tag) {
841
    acc_type = ptno(son(acc));
842
    if (no_frame && acc_type != reg_pl)
843
      return;
844
  }
845
  if (name(acc)!= name_tag) {
846
    fprintf(dg_file, "\t.stabs\t\"%s=i\",0x80,0,0,%d\n",
847
	d -> data.id_scope.nme.ints.chars, no(acc));
848
  }
849
  else
850
  if (acc_type == reg_pl) {
851
    fprintf(dg_file, "\t.stabs\t\"%s:r",
852
	d -> data.id_scope.nme.ints.chars);
853
    OUT_DT_SHAPE(d -> data.id_scope.typ);
854
    fprintf(dg_file, "\",0x40,0,0,%d\n",
855
		reg_stabno[get_reg_no(no(son(acc)))]);
856
  }
857
  else
858
#endif
859
  {
860
    p = (no(acc) + no(son(acc))) / 8;
861
    param_dec = isparam(son(acc));
862
 
863
    fprintf(dg_file, "\t.stabs\t\"%s:",
864
	d -> data.id_scope.nme.ints.chars);
865
    OUT_DT_SHAPE(d -> data.id_scope.typ);
866
    fprintf(dg_file, "\",0x80,0,%d,",
867
 
868
    if (param_dec)
869
      fprintf(dg_file, "%d\n", p+8);
870
    else
871
      fprintf(dg_file, "%d-%sdisp%d\n", p, local_prefix, proc_no);
872
  }
873
  return;
874
}
875
 
876
 
877
 
878
/*
879
    DEAL WITH BASIC TYPES
880
*/
881
 
882
static void stab_types
883
(void)
884
{
885
    total_type_sizes = NO_STABS;
886
    typeno = NO_STABS;
887
    type_sizes = (long *)xmalloc(NO_STABS * sizeof(long));
888
    fputs("\t.stabs\t\"int:t1=r1;-2147483648;2147483647;\",0x80,0,0,0\n",
889
	    dg_file);
890
    fputs("\t.stabs\t\"short int:t2=r1;-32768;32767;\",0x80,0,0,0\n",
891
	    dg_file);
892
    fputs("\t.stabs\t\"short unsigned int:t3=r1;0;65535;\",0x80,0,0,0\n",
893
	    dg_file);
894
    fputs("\t.stabs\t\"char:t4=r4;0;127;\",0x80,0,0,0\n",
895
	    dg_file);
896
    fputs("\t.stabs\t\"signed char:t5=r1;-128;127;\",0x80,0,0,0\n",
897
	    dg_file);
898
    fputs("\t.stabs\t\"unsigned char:t6=r1;0;255;\",0x80,0,0,0\n",
899
	    dg_file);
900
    fputs("\t.stabs\t\"long int:t7=r1;-2147483648;2147483647;\",0x80,0,0,0\n",
901
	    dg_file);
902
    fputs("\t.stabs\t\"unsigned int:t8=r1;0;-1;\",0x80,0,0,0\n",
903
	    dg_file);
904
    fputs("\t.stabs\t\"long unsigned int:t9=r1;0;-1;\",0x80,0,0,0\n",
905
	    dg_file);
906
    fputs("\t.stabs\t\"float:t10=r1;4;0;\",0x80,0,0,0\n",
907
	    dg_file);
908
    fputs("\t.stabs\t\"double:t11=r1;8;0;\",0x80,0,0,0\n",
909
	    dg_file);
910
    fprintf(dg_file, "\t.stabs\t\"long double:t12=r1;%d;0;\",0x80,0,0,0\n",
911
	      DOUBLE_SZ / 8);
912
    fputs("\t.stabs\t\"void:t13=13\",0x80,0,0,0\n",
913
	    dg_file);
914
    fputs("\t.stabs\t\"long long int:t14=r1;", dg_file);
915
    fputs("01000000000000000000000;0777777777777777777777;\",0x80,0,0,0\n",
916
	    dg_file);
917
    fputs("\t.stabs\t\"unsigned long long int:t15=r1;", dg_file);
918
    fputs("0000000000000;01777777777777777777777;\",0x80,0,0,0\n",
919
	    dg_file);
920
    type_sizes[0] = 0;
921
    type_sizes[1] = 32;
922
    type_sizes[2] = 16;
923
    type_sizes[3] = 16;
924
    type_sizes[4] = 8;
925
    type_sizes[5] = 8;
926
    type_sizes[6] = 8;
927
    type_sizes[7] = 32;
928
    type_sizes[8] = 32;
929
    type_sizes[9] = 32;
930
    type_sizes[10] = 32;
931
    type_sizes[11] = 64;
932
    type_sizes[12] = DOUBLE_SZ;
933
    type_sizes[13] = 0;
934
    type_sizes[14] = 64;
935
    type_sizes[15] = 64;
936
    return;
937
}
938
 
939
 
940
/*
941
    DEAL WITH STRUCTURE, UNION AND ENUM TAGS
942
*/
943
 
944
void stab_tagdefs
945
(void)
946
{
947
    diag_tagdef **di = unit_ind_diagtags;
948
    int i, n = unit_no_of_diagtags, istag;
949
 
950
    for (i = 0; i < n; i++) {
951
	diag_type d = di[i] ->d_type;
952
	istag = 1;
953
 
954
	switch (d->key) {
955
 
956
	    case DIAG_TYPE_STRUCT: {
957
		char *nme = d->data.t_struct.nme.ints.chars;
958
		if (nme && *nme) {
959
		    fprintf(dg_file, "\t.stabs\t\"%s:", nme);
960
		} else {
961
		    static int s_count = 0;
962
		    fprintf(dg_file, "\t.stabs\t\"_struct%d:", s_count++);
963
		}
964
		break;
965
	    }
966
	    case DIAG_TYPE_UNION: {
967
		char *nme = d->data.t_union.nme.ints.chars;
968
		if (nme && *nme) {
969
		    fprintf(dg_file, "\t.stabs\t\"%s:", nme);
970
		} else {
971
		    static int u_count = 0;
972
		    fprintf(dg_file, "\t.stabs\t\"_union%d:", u_count++);
973
		}
974
		break;
975
	    }
976
	    case DIAG_TYPE_ENUM: {
977
		char *nme = d->data.t_enum.nme.ints.chars;
978
		if (nme && *nme) {
979
		    fprintf(dg_file, "\t.stabs\t\"%s:", nme);
980
		} else {
981
		    static int e_count = 0;
982
		    fprintf(dg_file, "\t.stabs\t\"_enum%d:", e_count++);
983
		}
984
		break;
985
	    }
986
	    default: {
987
		istag = 0;
988
		break;
989
	    }
990
	}
991
	if (istag) {
992
	    if (d->been_outed && 0) {
993
		fprintf(dg_file, "%d",(int)d->been_outed);
994
	    } else {
995
		fprintf(dg_file, "T");
996
		OUT_DT_SHAPE(d);
997
	    }
998
	    fprintf(dg_file, "\",0x80,0,0,0\n");
999
	}
1000
    }
1001
    return;
1002
}
1003
 
1004
 
1005
/*
1006
    DEAL WITH TYPEDEFS
1007
*/
1008
 
1009
void stab_typedefs
1010
(void)
1011
{
1012
    diag_descriptor *di = unit_diagvar_tab.array;
1013
    int i, n = unit_diagvar_tab.lastused;
1014
    for (i = 0; i < n; i++) {
1015
	if (di[i].key == DIAG_TYPEDEF_KEY) {
1016
	    long non = next_typen();
1017
	    fprintf(dg_file, "\t.stabs\t\"%s:t%ld=",
1018
		      di[i].data.typ.nme.ints.chars, non);
1019
	    OUT_DT_SHAPE(di[i].data.typ.new_type);
1020
	    fprintf(dg_file, "\",0x80,0,0,0\n");
1021
	}
1022
    }
1023
    return;
1024
}