Subversion Repositories tendra.SVN

Rev

Rev 5 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 7u83 1
/*
6 7u83 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
/*
2 7u83 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
/**********************************************************************
62
$Author: release $
63
$Date: 1998/02/04 10:43:38 $
64
$Revision: 1.2 $
65
$Log: dwarf_type.c,v $
66
 * Revision 1.2  1998/02/04  10:43:38  release
67
 * Changes during testing.
68
 *
69
 * Revision 1.1.1.1  1998/01/17  15:55:48  release
70
 * First version to be checked into rolling release.
71
 *
72
 * Revision 1.7  1996/07/05  09:03:58  pwe
73
 * correction for enums
74
 *
75
 * Revision 1.6  1996/03/13  13:50:37  pwe
76
 * diags for long long
77
 *
78
 * Revision 1.5  1995/11/28  13:40:31  pwe
79
 * int more likely than long for 32 bit
80
 *
81
 * Revision 1.4  1995/09/28  12:40:00  pwe
82
 * dwarf.h via import, and type changes for tcc checks
83
 *
84
 * Revision 1.3  1995/09/13  16:13:18  pwe
85
 * tidy for gcc
86
 *
87
 * Revision 1.2  1995/09/13  14:25:41  pwe
88
 * tidy for gcc
89
 *
90
 * Revision 1.1.1.1  1995/08/14  14:30:25  pwe
91
 * transferred from DJCH
92
 *
93
**********************************************************************/
94
 
95
/* LOG 3/6/93 added extra message to is_fund_dwarf when using
96
   non-diag libraries djch */
97
/* LOG 7/9/93 changes for SPARC SVR4.2 to abstract asm directives djch */
98
/* LOG 25/11/93 renamed SET to DOT_SET to free SET for pwc's use djch */
99
 
100
#include "config.h"
101
#include "common_types.h"
102
#include "installtypes.h"
103
#include "machine.h"
104
#include "out.h"
105
#include "shapemacs.h"
106
#include "expmacs.h"
107
#include "basicread.h"
108
#include "xalloc.h"
109
 
110
#include "dwarf_types.h"
111
#include "dwarf_out.h"
112
#include "dwarf_queue.h"
113
#include "dwarf_loc.h"
114
#include "dwarf_type.h"
115
#include "cross_config.h"
116
 
117
#ifndef CROSS_INCLUDE
118
#include <dwarf.h>
119
#else
120
#include CROSS_INCLUDE/dwarf.h>
121
#endif
122
 
6 7u83 123
#define NOT_YET(x)	fprintf(stderr, "%s not yet implemented\n", x)
2 7u83 124
 
6 7u83 125
#define BEEN_PUT_OUT(x)	((x)->been_outed != NULL)
2 7u83 126
 
127
#define gcc_FT_long_long		0x8008
128
#define gcc_FT_unsigned_long_long	0x8208
129
 
6 7u83 130
static int
131
is_fund_dwarf(diag_type t)
2 7u83 132
{
6 7u83 133
	switch (t->key) {
134
	case DIAG_TYPE_ARRAY:
135
	case DIAG_TYPE_PROC:
136
	case DIAG_TYPE_STRUCT:
137
	case DIAG_TYPE_ENUM:
138
	case DIAG_TYPE_UNION:
139
		return 0;
2 7u83 140
 
6 7u83 141
	case DIAG_TYPE_FLOAT:
142
	case DIAG_TYPE_VARIETY:
143
	case DIAG_TYPE_NULL:
144
	case DIAG_TYPE_BITFIELD:
145
		return 1;
2 7u83 146
 
6 7u83 147
	case DIAG_TYPE_LOC:
148
		return is_fund_dwarf(t->data.loc.object);
149
	case DIAG_TYPE_PTR:
150
		return is_fund_dwarf(t->data.ptr.object);
151
	case DIAG_TYPE_INITED:
152
		failer("Initialized but undefined diag type in is_fund_dwarf - may be caused by using libraries without diagnostic information");
153
	case DIAG_TYPE_UNINIT:
154
	default:
155
		failer("Illegal diag type in is_fund_dwarf");
156
	}
157
	exit(EXIT_FAILURE);
2 7u83 158
}
159
 
6 7u83 160
 
161
static void
162
out_plain_fund_attr(diag_type t)
2 7u83 163
{
6 7u83 164
	switch (t->key) {
165
	case DIAG_TYPE_FLOAT:
166
		/* magic numbers from install_fns.c */
167
		switch(t->data.f_var) {
168
		case 0:
169
			dwarf2c(FT_float);
170
			break;
171
		case 1:
172
			dwarf2c(FT_dbl_prec_float);
173
			break;
174
		case 2:
175
			dwarf2c(FT_ext_prec_float);
176
			break;
177
		default:
178
			failer("unknown float type");
179
			exit(EXIT_FAILURE);
180
		}
181
		break;
182
	case DIAG_TYPE_VARIETY:
183
		switch (name(t->data.var)) {
184
		case scharhd:
185
			dwarf2c(FT_signed_char);
186
			break;
187
		case ucharhd:
188
			dwarf2c(FT_unsigned_char);
189
			break;
190
		case swordhd:
191
			dwarf2c(FT_signed_short);
192
			break;
193
		case uwordhd:
194
			dwarf2c(FT_unsigned_short);
195
			break;
196
		case slonghd:
197
			dwarf2c(FT_signed_integer);
198
			break;
199
		case ulonghd:
200
			dwarf2c(FT_unsigned_integer);
201
			break;
202
		case s64hd:
203
			dwarf2c(gcc_FT_long_long);
204
			break;
205
		case u64hd:
206
			dwarf2c(gcc_FT_unsigned_long_long);
207
			break;
208
		default:
209
			failer("Unknown int type");
210
			exit(EXIT_FAILURE);
211
		}
212
		break;
213
	case DIAG_TYPE_BITFIELD:
214
		out_plain_fund_attr(t->data.bitfield.result_type);
215
		if (t->data.bitfield.result_type->key != DIAG_TYPE_VARIETY) {
216
			failer("non variety base type in bitfield");
217
		}
218
		out_dwarf_bytesize_attr(t->data.bitfield.result_type->data.var);
219
		OUT_DWARF_ATTR(AT_bit_size);
220
		dwarf4n((int)t->data.bitfield.no_of_bits.nat_val.small_nat);
221
		break;
222
	case DIAG_TYPE_NULL:
223
		dwarf2c(FT_void);
224
		break;
225
	case DIAG_TYPE_PTR:
226
		if (t->data.ptr.object->key != DIAG_TYPE_NULL) {
227
			failer("non void ptr in out_plain_fund_attr");
228
		}
229
		dwarf2c(FT_pointer);
230
		break;
231
	default:
232
		failer("wrong type in out_plain_fund_attr");
233
		exit(EXIT_FAILURE);
234
	}
2 7u83 235
}
236
 
6 7u83 237
 
238
static int
239
is_qualified(diag_type t)
2 7u83 240
{
6 7u83 241
	switch (t->key) {
242
	case DIAG_TYPE_LOC:
243
		/* yes if const/volatile */
244
		if (t->data.loc.qualifier.is_const ||
245
		    t->data.loc.qualifier.is_volatile) {
246
			return 1;
247
		}
248
		return is_qualified(t->data.loc.object);
249
	case DIAG_TYPE_PTR:
250
		/* definit-ish yes */
251
		/* EXCEPT that pointer to void is DWARF'ed as FT_pointer */
252
		if (t->data.ptr.qualifier.is_const ||
253
		    t->data.ptr.qualifier.is_volatile) {
254
			return 1;
255
		}
256
		if (t->data.ptr.object->key != DIAG_TYPE_NULL) {
257
			return 1;
258
		}
259
		/* I dont think that void can be qualified thus we won't
260
		 * recurse to the void*/
261
	default:
262
		return 0;
263
	}
2 7u83 264
}
265
 
6 7u83 266
 
267
static void
268
out_quals(diag_tq t)
2 7u83 269
{
6 7u83 270
	if (t.is_const) {
271
		dwarf1(MOD_const);
272
	}
273
	if (t.is_volatile) {
274
		dwarf1(MOD_volatile);
275
	}
2 7u83 276
}
277
 
6 7u83 278
 
279
static diag_type
280
dequalify(diag_type t)
2 7u83 281
{
6 7u83 282
	/* get to base and output mods */
283
	/* QUALIFERS */
284
	switch (t->key) {
285
	case DIAG_TYPE_LOC:
286
		out_quals(t->data.loc.qualifier);
287
		return(dequalify(t->data.loc.object));
288
	case DIAG_TYPE_PTR:
289
		if (t->data.ptr.object->key == DIAG_TYPE_NULL) {
290
			/* NOT a plain diag_type, fudge for void * */
291
			return t;
292
		}
293
		dwarf1(MOD_pointer_to);
294
		out_quals(t->data.ptr.qualifier);
295
		/* qualifiers to the thing being pointed to */
296
		return(dequalify(t->data.ptr.object));
297
	default:
298
		return t;
299
	}
2 7u83 300
}
301
 
6 7u83 302
 
303
diag_type
304
base_type(diag_type t)
2 7u83 305
{
6 7u83 306
	switch (t->key) {
307
	case DIAG_TYPE_LOC:
308
		return(base_type(t->data.loc.object));
309
	case DIAG_TYPE_PTR:
310
		return(base_type(t->data.ptr.object));
311
	default:
312
		return t;
313
	}
2 7u83 314
}
315
 
6 7u83 316
 
317
static void
318
out_fund_attr(diag_type t)
2 7u83 319
{
6 7u83 320
	if (is_qualified(t)) {
321
		OUT_DWARF_ATTR(AT_mod_fund_type);
322
		new_dwarf_blk2();
323
		out_plain_fund_attr(dequalify(t));
324
		leave_dwarf_blk2();
325
	} else {
326
		OUT_DWARF_ATTR(AT_fund_type);
327
		out_plain_fund_attr((t->key == DIAG_TYPE_LOC) ?
328
				    t->data.loc.object : t);
329
	}
2 7u83 330
}
331
 
6 7u83 332
 
333
static void
334
out_plain_user_attr(diag_type t)
2 7u83 335
{
6 7u83 336
	/*  this NEVER writes out the actual TAG_xxxx block, but instead
337
	    outputs the FORM_REF 4 byte offset of the actual block */
338
	if (!BEEN_PUT_OUT(t)) {
339
		failer("out_plain_user_attr without an asm label");
340
		exit(EXIT_FAILURE);
341
	}
342
	dwarf4(&((*t->been_outed)[0]));
2 7u83 343
}
344
 
6 7u83 345
 
346
static void
347
out_user_attr(diag_type t)
2 7u83 348
{
6 7u83 349
	if (is_qualified(t)) {
350
		OUT_DWARF_ATTR(AT_mod_u_d_type);
351
		new_dwarf_blk2();
352
		out_plain_user_attr(dequalify(t));
353
		leave_dwarf_blk2();
354
	} else {
355
		OUT_DWARF_ATTR(AT_user_def_type);
356
		out_plain_user_attr((t->key == DIAG_TYPE_LOC) ?
357
				    t->data.loc.object : t);
358
	}
2 7u83 359
}
360
 
6 7u83 361
 
362
static void
363
queue_up_type_out(diag_type t)
2 7u83 364
{
6 7u83 365
	if (BEEN_PUT_OUT(t)) {
366
		failer("Whhops, queueing twice");
367
		return;
368
	}
369
	t->been_outed = next_dwarf_type_lab();
370
	add_type_q(t);
2 7u83 371
}
372
 
6 7u83 373
 
374
void
375
out_dwarf_type_attr(diag_type t)
2 7u83 376
{
6 7u83 377
	/* output a dwarf type as an attribute if done once already then just
378
	 * the attr, else queue the type, then the attr */
379
	if (is_fund_dwarf(t)) {
380
		out_fund_attr(t);
381
		return;
382
	}
383
	{
384
		diag_type b = base_type(t);
385
		if (!BEEN_PUT_OUT(b)) {
386
			/* this will assign the label value */
387
			queue_up_type_out(b);
388
		}
2 7u83 389
 
6 7u83 390
		out_user_attr(t);
391
		return;
392
	}
2 7u83 393
}
394
 
6 7u83 395
 
396
void
397
out_dwarf_user_type(diag_type t)
2 7u83 398
{
6 7u83 399
	if (!BEEN_PUT_OUT(t)) {
400
		/* if so then no external refs */
401
		t->been_outed = next_dwarf_type_lab();
402
	}
403
	switch (t->key) {
404
	case DIAG_TYPE_ARRAY:
405
		cont_sib_chain(TAG_array_type);
2 7u83 406
 
6 7u83 407
		OUT_DWARF_ATTR(AT_stride_size);
408
		out_dwarf_const_by8(t->data.array.stride);
409
		/* out_dwarf_name_attr(t->data.array.name); */
410
		OUT_DWARF_ATTR(AT_subscr_data);
411
		new_dwarf_blk2();
412
		dwarf1((int)FMT_FT_C_C);
413
		OUT_DWARF_TAG(FT_signed_integer);
414
		out_dwarf_const4(t->data.array.lower_b);
415
		/* FOR C this is one too big */
416
		out_dwarf_const4(t->data.array.upper_b);
417
		dwarf1((int)FMT_ET);
418
		out_dwarf_type_attr(t->data.array.element_type);
419
		leave_dwarf_blk2();
420
		break;
421
	case DIAG_TYPE_ENUM:
422
		cont_sib_chain(TAG_enumeration_type);
423
		out_dwarf_name_attr(TDFSTRING2CHAR(t->data.t_enum.nme));
424
		if (t->data.t_enum.base_type->key != DIAG_TYPE_VARIETY) {
425
			failer("non integral enum type");
426
		}
427
		out_dwarf_bytesize_attr(t->data.t_enum.base_type->data.var);
428
		OUT_DWARF_ATTR(AT_element_list);
429
		new_dwarf_blk4();
430
		{
431
			int i;
432
			enum_values *a = t->data.t_enum.values->array;
2 7u83 433
 
6 7u83 434
			for (i=0; i<t->data.t_enum.values->lastused; i++) {
435
				out_dwarf_const4(a[i]->val);
436
				out_dwarf_string(TDFSTRING2CHAR(a[i]->nme));
437
			}
438
		}
439
		leave_dwarf_blk4();
440
		break;
441
	case DIAG_TYPE_PROC:
442
		cont_sib_chain(TAG_subroutine_type);
443
		out_dwarf_type_attr(t->data.proc.result_type);
444
		break;
445
	case DIAG_TYPE_STRUCT:
446
		cont_sib_chain(TAG_structure_type);
447
		out_dwarf_name_attr(TDFSTRING2CHAR(t->data.t_struct.nme));
448
		out_dwarf_bytesize_attr(t->data.t_struct.tdf_shape);
449
		break;
450
	case DIAG_TYPE_UNION:
451
		cont_sib_chain(TAG_union_type);
452
		out_dwarf_name_attr(TDFSTRING2CHAR(t->data.t_union.nme));
453
		out_dwarf_bytesize_attr(t->data.t_union.tdf_shape);
454
		break;
455
	default:
456
		failer("Illegal diag type in out_dwarf_user_type");
457
	}
458
	/* now we must set the dwarf type label
459
	   to be the dwarf label of this block */
460
	{
461
		char expr_buf[100];
2 7u83 462
#if (is80x86)
6 7u83 463
#define DOT_SET	".set"
2 7u83 464
#else
465
#if (issparc)
466
#else
6 7u83 467
		error need the .set directive
2 7u83 468
#endif
469
#endif
470
 
471
#if FS_CONCAT_STRING
472
#if (is80x86)
6 7u83 473
#define SET_F	"\t"DOT_SET"\t%s , %s"
2 7u83 474
#else
475
#if (issparc)
6 7u83 476
#define SET_F	"\t%s = %s"
2 7u83 477
#else
6 7u83 478
		error need set format str
2 7u83 479
#endif
480
#endif
481
#else
482
#if (issparc)
483
/* KEEP this in step..... */
6 7u83 484
#define SET_F	"\t%s = %s"
2 7u83 485
#else
486
#if (is80x86)
6 7u83 487
#define SET_F	"\t.set\t %s , %s"
2 7u83 488
#else
6 7u83 489
		error write this
2 7u83 490
#endif
491
#endif
492
#endif
493
 
494
#ifdef mips
6 7u83 495
		sprintf(expr_buf, SET_F, (char *)t->been_outed,
2 7u83 496
#else
6 7u83 497
		sprintf(expr_buf, SET_F, (char *)&((t->been_outed)[0]),
2 7u83 498
#endif
6 7u83 499
			current_label_name());
500
		outs(expr_buf);
501
		outnl();
502
		}
503
		leave_dwarf_blk();
2 7u83 504
 
6 7u83 505
		switch (t->key) {
506
		case DIAG_TYPE_PROC: {
507
			int i;
508
			diag_type_list pars = t->data.proc.params;
2 7u83 509
 
6 7u83 510
			make_next_new_chain();
511
			for (i = 0; i< pars->lastused; i++) {
512
				cont_sib_chain(TAG_formal_parameter);
513
				out_dwarf_type_attr(pars->array[i]);
514
				leave_dwarf_blk();
515
			}
516
			if (t->data.proc.opt_args) {
517
				cont_sib_chain(TAG_unspecified_parameters);
518
				leave_dwarf_blk();
519
			}
520
			end_sib_chain();
521
		}
522
			break;
523
		case DIAG_TYPE_STRUCT: {
524
			diag_field_list f = t->data.t_struct.fields;
525
			int i;
2 7u83 526
 
6 7u83 527
			make_next_new_chain();
528
			for (i = f->lastused-1 ;i>=0; i--) {
529
				diag_field m = f->array[i];
2 7u83 530
 
6 7u83 531
				cont_sib_chain(TAG_member);
532
				out_dwarf_name_attr(TDFSTRING2CHAR(m->field_name));
533
				out_dwarf_type_attr(m->field_type);
534
				if (m->field_type->key == DIAG_TYPE_BITFIELD) {
535
					/* dwarf describes bitfields wrt an
536
					 * anonymous object, whose size is that
537
					 * of the base type */
538
					int base_type_in_bits =
539
					    shape_size(m->field_type->data.bitfield.result_type->data.var);
540
					int bit_size =
541
					    m->field_type->data.bitfield.no_of_bits.nat_val.small_nat;
542
					int bit_offset_from_base =
543
					    (int)no(m->where);
544
					int bit_offset_in_anon_obj =
545
					    bit_offset_from_base %
546
					    base_type_in_bits;
547
					int bit_offset_to_anon_obj =
548
					    bit_offset_from_base -
549
					    bit_offset_in_anon_obj;
2 7u83 550
 
6 7u83 551
					OUT_DWARF_ATTR(AT_bit_offset);
552
					out_dwarf_thing((int)
2 7u83 553
#if (little_end)
6 7u83 554
					  /* count from other end  */
555
					((base_type_in_bits -
556
					  bit_offset_in_anon_obj) - bit_size)
2 7u83 557
#else
6 7u83 558
					bit_offset_in_anon_obj
2 7u83 559
#endif
6 7u83 560
					," bits");
561
					out_dwarf_bit_member_loc_attr(bit_offset_to_anon_obj);
562
				} else {
563
					out_dwarf_member_loc_attr(m->where);
564
				}
565
				leave_dwarf_blk();
566
			}
567
			end_sib_chain();
568
		}
569
			break;
570
		case DIAG_TYPE_UNION: {
571
			diag_field_list f = t->data.t_union.fields;
572
			int i;
2 7u83 573
 
6 7u83 574
			make_next_new_chain();
575
			for (i = f->lastused - 1; i >= 0; i--) {
576
				diag_field m = f->array[i];
2 7u83 577
 
6 7u83 578
				cont_sib_chain(TAG_member);
579
				out_dwarf_name_attr(TDFSTRING2CHAR(m->field_name));
580
				out_dwarf_type_attr(m->field_type);
581
				out_dwarf_member_loc_attr(m->where);
582
				leave_dwarf_blk();
583
			}
584
			end_sib_chain();
585
		}
586
			    break;
587
		default:
588
			    break;
589
		}
2 7u83 590
}