Warning: Undefined variable $n in /usr/local/www/websvn.planix.org/include/diff_util.php on line 243

Warning: Undefined variable $n in /usr/local/www/websvn.planix.org/include/diff_util.php on line 247

Warning: Undefined variable $m in /usr/local/www/websvn.planix.org/include/diff_util.php on line 251
WebSVN – tendra.SVN – Diff – /trunk/src/producers/common/output/unmangle.c – Rev 2 and 7

Subversion Repositories tendra.SVN

Rev

Rev 2 | Show entire file | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 2 Rev 7
Line -... Line 1...
-
 
1
/*
-
 
2
 * Copyright (c) 2002-2006 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
 */
1
/*
31
/*
2
    		 Crown Copyright (c) 1997
32
    		 Crown Copyright (c) 1997
3
    
33
 
4
    This TenDRA(r) Computer Program is subject to Copyright
34
    This TenDRA(r) Computer Program is subject to Copyright
5
    owned by the United Kingdom Secretary of State for Defence
35
    owned by the United Kingdom Secretary of State for Defence
6
    acting through the Defence Evaluation and Research Agency
36
    acting through the Defence Evaluation and Research Agency
7
    (DERA).  It is made available to Recipients with a
37
    (DERA).  It is made available to Recipients with a
8
    royalty-free licence for its use, reproduction, transfer
38
    royalty-free licence for its use, reproduction, transfer
9
    to other parties and amendment for any purpose not excluding
39
    to other parties and amendment for any purpose not excluding
10
    product development provided that any such use et cetera
40
    product development provided that any such use et cetera
11
    shall be deemed to be acceptance of the following conditions:-
41
    shall be deemed to be acceptance of the following conditions:-
12
    
42
 
13
        (1) Its Recipients shall ensure that this Notice is
43
        (1) Its Recipients shall ensure that this Notice is
14
        reproduced upon any copies or amended versions of it;
44
        reproduced upon any copies or amended versions of it;
15
    
45
 
16
        (2) Any amended version of it shall be clearly marked to
46
        (2) Any amended version of it shall be clearly marked to
17
        show both the nature of and the organisation responsible
47
        show both the nature of and the organisation responsible
18
        for the relevant amendment or amendments;
48
        for the relevant amendment or amendments;
19
    
49
 
20
        (3) Its onward transfer from a recipient to another
50
        (3) Its onward transfer from a recipient to another
21
        party shall be deemed to be that party's acceptance of
51
        party shall be deemed to be that party's acceptance of
22
        these conditions;
52
        these conditions;
23
    
53
 
24
        (4) DERA gives no warranty or assurance as to its
54
        (4) DERA gives no warranty or assurance as to its
25
        quality or suitability for any purpose and DERA accepts
55
        quality or suitability for any purpose and DERA accepts
26
        no liability whatsoever in relation to any use to which
56
        no liability whatsoever in relation to any use to which
27
        it may be put.
57
        it may be put.
28
*/
58
*/
Line 82... Line 112...
82
 
112
 
83
    The following forward declarations are required in the name unmangling
113
    The following forward declarations are required in the name unmangling
84
    routines.
114
    routines.
85
*/
115
*/
86
 
116
 
87
static NAT unmangle_nat PROTO_S ( ( string * ) ) ;
117
static NAT unmangle_nat(string *);
88
static TYPE unmangle_type PROTO_S ( ( string *, CV_SPEC, BASE_TYPE, int ) ) ;
118
static TYPE unmangle_type(string *, CV_SPEC, BASE_TYPE, int);
89
static IDENTIFIER unmangle_nspace PROTO_S ( ( string *, NAMESPACE, int ) ) ;
119
static IDENTIFIER unmangle_nspace(string *, NAMESPACE, int);
90
static LIST ( TOKEN ) unmangle_token_args PROTO_S ( ( string * ) ) ;
120
static LIST(TOKEN)unmangle_token_args(string *);
91
static TOKEN find_token_arg PROTO_S ( ( string * ) ) ;
121
static TOKEN find_token_arg(string *);
92
 
122
 
93
 
123
 
94
/*
124
/*
95
    DUMMY RETURN TYPE
125
    DUMMY RETURN TYPE
96
 
126
 
97
    This variable is a dummy used as a return type when none is given in
127
    This variable is a dummy used as a return type when none is given in
98
    a mangled form.  Its printed form is empty.
128
    a mangled form.  Its printed form is empty.
99
*/
129
*/
100
 
130
 
101
static TYPE dummy_ret_type = NULL_type ;
131
static TYPE dummy_ret_type = NULL_type;
102
 
132
 
103
 
133
 
104
/*
134
/*
105
    CURRENT UNMANGLING INFORMATION
135
    CURRENT UNMANGLING INFORMATION
106
 
136
 
107
    The following variables are used to hold certain information about the
137
    The following variables are used to hold certain information about the
108
    identifier being unmangled.
138
    identifier being unmangled.
109
*/
139
*/
110
 
140
 
111
static IDENTIFIER crt_unmangle_class = NULL_id ;
141
static IDENTIFIER crt_unmangle_class = NULL_id;
112
static LIST ( TOKEN ) crt_unmangle_args = NULL_list ( TOKEN ) ;
142
static LIST(TOKEN)crt_unmangle_args = NULL_list(TOKEN);
113
 
143
 
114
 
144
 
115
/*
145
/*
116
    UNMANGLE AN OPERATOR NAME
146
    UNMANGLE AN OPERATOR NAME
117
 
147
 
118
    This routine unmangles an operator name from the string pointed to
148
    This routine unmangles an operator name from the string pointed to
119
    by ps.
149
    by ps.
210
	}
414
	}
211
	case 'd' : {
415
	case 's': {
212
	    c = *( s++ ) ;
416
		c = *(s++);
213
	    switch ( c ) {
417
		if (c == 'z') {
214
		case 'f' : t = lex_dot ; break ;
-
 
215
		case 'l' : t = lex_delete ; break ;
-
 
216
		case 'm' : t = lex_dot_Hstar ; break ;
-
 
217
		case 't' : t = lex_destructor_Hname ; break ;
-
 
218
		case 'v' : t = lex_div ; break ;
418
			t = lex_sizeof;
219
	    }
419
		}
220
	    break ;
420
		break;
221
	}
421
	}
222
	case 'e' : {
422
	case 't': {
223
	    c = *( s++ ) ;
423
		c = *(s++);
224
	    switch ( c ) {
424
		switch (c) {
225
		case 'q' : t = lex_eq ; break ;
-
 
226
		case 'r' : t = lex_xor_H1 ; break ;
-
 
227
	    }
-
 
228
	    break ;
-
 
229
	}
-
 
230
	case 'f' : {
425
		case 'b':
231
	    t = lex_float ;
426
			t = lex_vtable;
232
	    break ;
427
			break;
233
	}
-
 
234
	case 'g' : {
428
		case 'd':
235
	    c = *( s++ ) ;
429
			t = lex_typeid;
236
	    switch ( c ) {
-
 
237
		case 'e' : t = lex_greater_Heq ; break ;
-
 
238
		case 't' : t = lex_greater ; break ;
-
 
239
	    }
-
 
240
	    break ;
430
			break;
241
	}
-
 
242
	case 'l' : {
431
		case 'i': {
243
	    c = *( s++ ) ;
-
 
244
	    switch ( c ) {
-
 
245
		case 'e' : t = lex_less_Heq ; break ;
-
 
246
		case 's' : t = lex_lshift ; break ;
432
			if (s[0] == '_' && s[1] == '_') {
247
		case 't' : t = lex_less ; break ;
-
 
248
	    }
-
 
249
	    break ;
-
 
250
	}
-
 
251
	case 'm' : {
-
 
252
	    c = *( s++ ) ;
433
				t = lex_typeof;
253
	    switch ( c ) {
-
 
254
		case 'd' : t = lex_rem ; break ;
-
 
255
		case 'i' : t = lex_minus ; break ;
-
 
256
		case 'l' : t = lex_star ; break ;
-
 
257
		case 'm' : t = lex_minus_Hminus ; break ;
-
 
258
		case 'n' : t = lex_min ; break ;
-
 
259
		case 'x' : t = lex_max ; break ;
-
 
260
	    }
-
 
261
	    break ;
-
 
262
	}
-
 
263
	case 'n' : {
434
				s += 2;
264
	    c = *( s++ ) ;
-
 
265
	    switch ( c ) {
-
 
266
		case 'e' : t = lex_not_Heq_H1 ; break ;
-
 
267
		case 't' : t = lex_not_H1 ; break ;
-
 
268
		case 'w' : t = lex_new ; break ;
-
 
269
	    }
-
 
270
	    break ;
-
 
271
	}
435
			}
272
	case 'o' : {
-
 
273
	    c = *( s++ ) ;
-
 
274
	    switch ( c ) {
-
 
275
		case 'o' : t = lex_logical_Hor_H1 ; break ;
-
 
276
		case 'p' : t = lex_operator ; break ;
-
 
277
		case 'r' : t = lex_or_H1 ; break ;
-
 
278
	    }
-
 
279
	    break ;
436
			break;
280
	}
437
		}
281
	case 'p' : {
-
 
282
	    c = *( s++ ) ;
-
 
283
	    switch ( c ) {
-
 
284
		case 'l' : t = lex_plus ; break ;
-
 
285
		case 'p' : t = lex_plus_Hplus ; break ;
-
 
286
	    }
-
 
287
	    break ;
-
 
288
	}
438
		}
289
	case 'r' : {
-
 
290
	    c = *( s++ ) ;
-
 
291
	    switch ( c ) {
-
 
292
		case 'f' : t = lex_arrow ; break ;
-
 
293
		case 'm' : t = lex_arrow_Hstar ; break ;
-
 
294
		case 's' : t = lex_rshift ; break ;
-
 
295
	    }
-
 
296
	    break ;
439
		break;
297
	}
440
	}
298
	case 's' : {
441
	case 'v': {
299
	    c = *( s++ ) ;
442
		c = *(s++);
-
 
443
		switch (c) {
-
 
444
		case 'c':
300
	    if ( c == 'z' ) t = lex_sizeof ;
445
			t = lex_array_Hop;
301
	    break ;
446
			break;
-
 
447
		case 'd':
-
 
448
			t = lex_delete_Harray;
302
	}
449
			break;
303
	case 't' : {
450
		case 'n':
304
	    c = *( s++ ) ;
451
			t = lex_new_Harray;
-
 
452
			break;
305
	    switch ( c ) {
453
		case '_':
306
		case 'b' : t = lex_vtable ; break ;
454
			t = lex_static;
307
		case 'd' : t = lex_typeid ; break ;
455
			break;
308
		case 'i' : {
456
		case 't': {
309
		    if ( s [0] == '_' && s [1] == '_' ) {
457
			if (s[0] == '_' && s[1] == '_') {
310
			t = lex_typeof ;
458
				t = lex_virtual;
311
			s += 2 ;
459
				s += 2;
312
		    }
460
			}
313
		    break ;
461
			break;
-
 
462
		}
314
		}
463
		}
315
	    }
-
 
316
	    break ;
-
 
317
	}
-
 
318
	case 'v' : {
-
 
319
	    c = *( s++ ) ;
-
 
320
	    switch ( c ) {
-
 
321
		case 'c' : t = lex_array_Hop ; break ;
-
 
322
		case 'd' : t = lex_delete_Harray ; break ;
-
 
323
		case 'n' : t = lex_new_Harray ; break ;
-
 
324
		case '_' : t = lex_static ; break ;
-
 
325
		case 't' : {
-
 
326
		    if ( s [0] == '_' && s [1] == '_' ) {
-
 
327
			t = lex_virtual ;
-
 
328
			s += 2 ;
-
 
329
		    }
-
 
330
		    break ;
464
		break;
331
		}
-
 
332
	    }
-
 
333
	    break ;
-
 
334
	}
-
 
335
	case '0' : case '1' : case '2' : case '3' : case '4' :
-
 
336
	case '5' : case '6' : case '7' : case '8' : case '9' : {
-
 
337
	    t = lex_auto ;
-
 
338
	    break ;
-
 
339
	}
465
	}
-
 
466
	case '0':
-
 
467
	case '1':
-
 
468
	case '2':
-
 
469
	case '3':
-
 
470
	case '4':
-
 
471
	case '5':
-
 
472
	case '6':
-
 
473
	case '7':
-
 
474
	case '8':
-
 
475
	case '9': {
-
 
476
		t = lex_auto;
-
 
477
		break;
-
 
478
	}
340
    }
479
	}
341
    if ( t != lex_unknown ) *ps = s ;
480
	if (t != lex_unknown) {
-
 
481
		*ps = s;
-
 
482
	}
342
    return ( t ) ;
483
	return (t);
343
}
484
}
344
 
485
 
345
 
486
 
346
/*
487
/*
347
    UNMANGLE A NUMBER
488
    UNMANGLE A NUMBER
348
 
489
 
349
    This routine unmangles a series of digits from the string pointed
490
    This routine unmangles a series of digits from the string pointed
350
    to by ps.  If e is true then the digits should be terminated by an
491
    to by ps.  If e is true then the digits should be terminated by an
351
    underscore.
492
    underscore.
352
*/
493
*/
353
 
494
 
354
static unsigned unmangle_no
495
static unsigned
355
    PROTO_N ( ( ps, e ) )
-
 
356
    PROTO_T ( string *ps X int e )
496
unmangle_no(string *ps, int e)
357
{
497
{
358
    character c ;
498
	character c;
359
    unsigned n = 0 ;
499
	unsigned n = 0;
360
    string s = *ps ;
500
	string s = *ps;
361
    while ( c = *( s++ ), ( c >= char_zero && c <= char_nine ) ) {
501
	while (c = *(s++), (c >= char_zero && c <= char_nine)) {
362
	unsigned d = ( unsigned ) ( c - char_zero ) ;
502
		unsigned d = (unsigned)(c - char_zero);
363
	n = 10 * n + d ;
503
		n = 10 * n + d;
364
    }
504
	}
365
    if ( c != MANGLE_sep || e == 0 ) s-- ;
505
	if (c != MANGLE_sep || e == 0) {
-
 
506
		s--;
-
 
507
	}
366
    *ps = s ;
508
	*ps = s;
367
    return ( n ) ;
509
	return (n);
368
}
510
}
369
 
511
 
370
 
512
 
371
/*
513
/*
372
    UNMANGLE A SMALL NUMBER
514
    UNMANGLE A SMALL NUMBER
373
 
515
 
374
    This routine unmangles a small number from the string pointed to
516
    This routine unmangles a small number from the string pointed to
375
    by ps.  This consists either of a single digit or a series of digits
517
    by ps.  This consists either of a single digit or a series of digits
376
    delimited by underscores.
518
    delimited by underscores.
377
*/
519
*/
378
 
520
 
379
static unsigned unmangle_digit
521
static unsigned
380
    PROTO_N ( ( ps ) )
-
 
381
    PROTO_T ( string *ps )
522
unmangle_digit(string *ps)
382
{
523
{
383
    unsigned n ;
524
	unsigned n;
384
    string s = *ps ;
525
	string s = *ps;
385
    character c = *( s++ ) ;
526
	character c = *(s++);
386
    if ( c >= char_zero && c <= char_nine ) {
527
	if (c >= char_zero && c <= char_nine) {
387
	n = ( unsigned ) ( c - char_zero ) ;
528
		n = (unsigned)(c - char_zero);
388
    } else if ( c == MANGLE_sep ) {
529
	} else if (c == MANGLE_sep) {
389
	n = unmangle_no ( &s, 1 ) ;
530
		n = unmangle_no(&s, 1);
390
    } else {
531
	} else {
391
	n = 0 ;
532
		n = 0;
392
	s-- ;
533
		s--;
393
    }
534
	}
394
    *ps = s ;
535
	*ps = s;
395
    return ( n ) ;
536
	return (n);
396
}
537
}
397
 
538
 
398
 
539
 
399
/*
540
/*
400
    UNMANGLE AN EXPRESSION
541
    UNMANGLE AN EXPRESSION
401
 
542
 
402
    This routine unmangles an expression of type t from the string pointed
543
    This routine unmangles an expression of type t from the string pointed
403
    to by ps.
544
    to by ps.
404
*/
545
*/
405
 
546
 
406
static EXP unmangle_exp
547
static EXP
407
    PROTO_N ( ( ps, t ) )
-
 
408
    PROTO_T ( string *ps X TYPE t )
548
unmangle_exp(string *ps, TYPE t)
409
{
549
{
410
    EXP e = NULL_exp ;
550
	EXP e = NULL_exp;
411
    string s = *ps ;
551
	string s = *ps;
412
    character c = *s ;
552
	character c = *s;
413
    if ( ( c >= char_zero && c <= char_nine ) || c == MANGLE_neg ) {
553
	if ((c >= char_zero && c <= char_nine) || c == MANGLE_neg) {
414
	/* Read an integer constant */
554
		/* Read an integer constant */
415
	NAT n = unmangle_nat ( &s ) ;
555
		NAT n = unmangle_nat(&s);
416
	if ( !IS_NULL_nat ( n ) ) {
556
		if (!IS_NULL_nat(n)) {
417
	    MAKE_exp_int_lit ( t, n, exp_int_lit_tag, e ) ;
557
			MAKE_exp_int_lit(t, n, exp_int_lit_tag, e);
418
	}
558
		}
419
 
559
 
420
    } else if ( c == MANGLE_op ) {
560
	} else if (c == MANGLE_op) {
421
	int op ;
561
		int op;
422
	s++ ;
562
		s++;
423
	op = unmangle_op ( &s ) ;
563
		op = unmangle_op(&s);
424
	if ( op == lex_float ) {
564
		if (op == lex_float) {
425
	    /* Floating point literals */
565
			/* Floating point literals */
426
	    string u = xustrcpy ( s ) ;
566
			string u = xustrcpy(s);
427
	    string v = u ;
567
			string v = u;
428
	    while ( c = *( s++ ), c != 0 ) {
568
			while (c = *(s++), c != 0) {
429
		if ( c == MANGLE_sep ) {
569
				if (c == MANGLE_sep) {
430
		    *v = 0 ;
570
					*v = 0;
431
		    s++ ;
571
					s++;
432
		    break ;
572
					break;
433
		}
573
				}
434
		if ( ( c >= char_zero && c <= char_nine ) || c == 'e' ) {
574
				if ((c >= char_zero && c <= char_nine) ||
-
 
575
				    c == 'e') {
435
		    /* EMPTY */
576
					/* EMPTY */
436
		} else if ( c == 'd' ) {
577
				} else if (c == 'd') {
437
		    *v = '.' ;
578
					*v = '.';
438
		} else if ( c == MANGLE_neg ) {
579
				} else if (c == MANGLE_neg) {
439
		    *v = '-' ;
580
					*v = '-';
440
		} else {
581
				} else {
441
		    *v = 0 ;
582
					*v = 0;
442
		    break ;
583
					break;
443
		}
584
				}
444
		v++ ;
585
				v++;
445
	    }
586
			}
446
	    s-- ;
587
			s--;
447
	    e = make_literal_exp ( u, &op, 0 ) ;
588
			e = make_literal_exp(u, &op, 0);
448
	} else {
589
		} else {
449
	    int n = 0 ;
590
			int n = 0;
450
	    c = *s ;
591
			c = *s;
451
	    if ( c >= char_zero && c <= char_nine ) {
592
			if (c >= char_zero && c <= char_nine) {
452
		n = ( int ) ( c - char_zero ) ;
593
				n = (int)(c - char_zero);
453
		s++ ;
594
				s++;
454
	    }
595
			}
455
	    if ( op == lex_sizeof ) {
596
			if (op == lex_sizeof) {
456
		TYPE r = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
597
				TYPE r = unmangle_type(&s, cv_none, btype_none,
-
 
598
						       1);
457
		e = make_sizeof_exp ( r, NULL_exp, 0, op ) ;
599
				e = make_sizeof_exp(r, NULL_exp, 0, op);
458
	    } else {
600
			} else {
459
		LIST ( EXP ) p = NULL_list ( EXP ) ;
601
				LIST(EXP)p = NULL_list(EXP);
460
		while ( n ) {
602
				while (n) {
461
		    EXP a = unmangle_exp ( &s, t ) ;
603
					EXP a = unmangle_exp(&s, t);
462
		    CONS_exp ( a, p, p ) ;
604
					CONS_exp(a, p, p);
463
		    n-- ;
605
					n--;
464
		}
606
				}
465
		p = REVERSE_list ( p ) ;
607
				p = REVERSE_list(p);
466
		MAKE_exp_opn ( t, op, p, e ) ;
608
				MAKE_exp_opn(t, op, p, e);
467
	    }
609
			}
468
	}
610
		}
469
 
611
 
470
    } else if ( c == MANGLE_sep ) {
612
	} else if (c == MANGLE_sep) {
471
	IDENTIFIER id ;
613
		IDENTIFIER id;
472
	s++ ;
614
		s++;
473
	id = unmangle_nspace ( &s, global_namespace, 1 ) ;
615
		id = unmangle_nspace(&s, global_namespace, 1);
474
	if ( !IS_NULL_id ( id ) ) {
616
		if (!IS_NULL_id(id)) {
475
	    MAKE_exp_identifier ( t, id, qual_nested, e ) ;
617
			MAKE_exp_identifier(t, id, qual_nested, e);
476
	}
618
		}
477
 
619
 
478
    } else if ( c == MANGLE_templ_param ) {
620
	} else if (c == MANGLE_templ_param) {
479
	/* Template parameter expressions */
621
		/* Template parameter expressions */
480
	TOKEN tok ;
622
		TOKEN tok;
481
	s++ ;
623
		s++;
482
	tok = find_token_arg ( &s ) ;
624
		tok = find_token_arg(&s);
483
	if ( !IS_NULL_tok ( tok ) && IS_tok_exp ( tok ) ) {
625
		if (!IS_NULL_tok(tok) && IS_tok_exp(tok)) {
484
	    e = DEREF_exp ( tok_exp_value ( tok ) ) ;
626
			e = DEREF_exp(tok_exp_value(tok));
485
	}
627
		}
486
    }
628
	}
487
    *ps = s ;
629
	*ps = s;
488
    return ( e ) ;
630
	return (e);
489
}
631
}
490
 
632
 
491
 
633
 
492
/*
634
/*
493
    UNMANGLE AN INTEGER CONSTANT
635
    UNMANGLE AN INTEGER CONSTANT
494
 
636
 
495
    This routine unmangles an integer constant from the string pointed to
637
    This routine unmangles an integer constant from the string pointed to
496
    by ps.
638
    by ps.
497
*/
639
*/
498
 
640
 
499
static NAT unmangle_nat
641
static NAT
500
    PROTO_N ( ( ps ) )
-
 
501
    PROTO_T ( string *ps )
642
unmangle_nat(string *ps)
502
{
643
{
503
    NAT n = NULL_nat ;
644
	NAT n = NULL_nat;
504
    string s = *ps ;
645
	string s = *ps;
505
    character c = *s ;
646
	character c = *s;
506
    if ( c >= char_zero && c <= char_nine ) {
647
	if (c >= char_zero && c <= char_nine) {
507
	/* Read a sequence of digits */
648
		/* Read a sequence of digits */
508
	s++ ;
649
		s++;
509
	do {
650
		do {
510
	    unsigned d = ( unsigned ) ( c - char_zero ) ;
651
			unsigned d = (unsigned)(c - char_zero);
511
	    n = make_nat_literal ( n, ( unsigned ) 10, d ) ;
652
			n = make_nat_literal(n,(unsigned)10, d);
512
	} while ( c = *( s++ ), ( c >= char_zero && c <= char_nine ) ) ;
653
		} while (c = *(s++), (c >= char_zero && c <= char_nine));
513
	if ( c != MANGLE_sep ) s-- ;
654
		if (c != MANGLE_sep) {
-
 
655
			s--;
-
 
656
		}
514
    } else if ( c == MANGLE_sep ) {
657
	} else if (c == MANGLE_sep) {
515
	/* Empty sequence of digits */
658
		/* Empty sequence of digits */
516
	s++ ;
659
		s++;
517
    } else if ( c == MANGLE_neg ) {
660
	} else if (c == MANGLE_neg) {
518
	/* Negate an integer */
661
		/* Negate an integer */
519
	s++ ;
662
		s++;
520
	n = unmangle_nat ( &s ) ;
663
		n = unmangle_nat(&s);
521
	n = negate_nat ( n ) ;
664
		n = negate_nat(n);
522
    } else {
665
	} else {
523
	/* Read an expression */
666
		/* Read an expression */
524
	EXP e = unmangle_exp ( &s, type_sint ) ;
667
		EXP e = unmangle_exp(&s, type_sint);
525
	if ( !IS_NULL_exp ( e ) ) {
668
		if (!IS_NULL_exp(e)) {
526
	    MAKE_nat_calc ( e, n ) ;
669
			MAKE_nat_calc(e, n);
-
 
670
		}
527
	}
671
	}
528
    }
-
 
529
    *ps = s ;
672
	*ps = s;
530
    return ( n ) ;
673
	return (n);
531
}
674
}
532
 
675
 
533
 
676
 
534
/*
677
/*
535
    UNMANGLE A NAMESPACE QUALIFIER
678
    UNMANGLE A NAMESPACE QUALIFIER
536
 
679
 
537
    This routine unmangles a namespace qualifier from the string pointed
680
    This routine unmangles a namespace qualifier from the string pointed
538
    to by ps.  Note that all such namespaces are declared as classes even
681
    to by ps.  Note that all such namespaces are declared as classes even
539
    if they are not in reality.
682
    if they are not in reality.
540
*/
683
*/
541
 
684
 
542
static IDENTIFIER unmangle_nspace
685
static IDENTIFIER
543
    PROTO_N ( ( ps, ns, var ) )
-
 
544
    PROTO_T ( string *ps X NAMESPACE ns X int var )
686
unmangle_nspace(string *ps, NAMESPACE ns, int var)
545
{
687
{
546
    string s = *ps ;
688
	string s = *ps;
547
    character c = *s ;
689
	character c = *s;
548
    IDENTIFIER id = NULL_id ;
690
	IDENTIFIER id = NULL_id;
549
    if ( c >= char_zero && c <= char_nine ) {
691
	if (c >= char_zero && c <= char_nine) {
550
	unsigned n = unmangle_no ( &s, 0 ) ;
692
		unsigned n = unmangle_no(&s, 0);
551
	if ( n ) {
693
		if (n) {
552
	    HASHID nm ;
694
			HASHID nm;
553
	    int ext = 0 ;
695
			int ext = 0;
554
	    TYPE t = NULL_type ;
696
			TYPE t = NULL_type;
555
	    string p = xustr ( ( gen_size ) ( n + 1 ) ) ;
697
			string p = xustr((gen_size)(n + 1));
556
	    string q = p ;
698
			string q = p;
557
	    while ( n ) {
699
			while (n) {
558
		c = *s ;
700
				c = *s;
559
		if ( c ) {
701
				if (c) {
560
		    if ( c == MANGLE_sep && s [1] == MANGLE_sep ) {
702
					if (c == MANGLE_sep && s[1] ==
-
 
703
					    MANGLE_sep) {
561
			/* Allow for unicode characters */
704
						/* Allow for unicode
-
 
705
						 * characters */
562
			if ( s [2] == MANGLE_unicode4 ) {
706
						if (s[2] == MANGLE_unicode4) {
563
			    *( q++ ) = char_backslash ;
707
							*(q++) = char_backslash;
564
			    c = char_u ;
708
							c = char_u;
565
			    ext = 1 ;
709
							ext = 1;
566
			    s += 2 ;
710
							s += 2;
-
 
711
						} else if (s[2] ==
567
			} else if ( s [2] == MANGLE_unicode8 ) {
712
							   MANGLE_unicode8) {
568
			    *( q++ ) = char_backslash ;
713
							*(q++) = char_backslash;
569
			    c = char_U ;
714
							c = char_U;
570
			    ext = 1 ;
715
							ext = 1;
571
			    s += 2 ;
716
							s += 2;
572
			}
717
						}
573
		    }
718
					}
574
		    *( q++ ) = c ;
719
					*(q++) = c;
575
		    s++ ;
720
					s++;
576
		} else {
721
				} else {
577
		    *( q++ ) = char_question ;
722
					*(q++) = char_question;
-
 
723
				}
-
 
724
				n--;
-
 
725
			}
-
 
726
			*q = 0;
-
 
727
			nm = lookup_name(p, hash(p), ext, lex_identifier);
-
 
728
			if (var) {
-
 
729
				t = type_sint;
-
 
730
				MAKE_id_variable(nm, dspec_extern, ns, crt_loc,
-
 
731
						 t, id);
-
 
732
			} else {
-
 
733
				id = make_class(ns, nm, btype_lang,
-
 
734
						dspec_extern, t, t);
-
 
735
			}
-
 
736
		}
-
 
737
 
-
 
738
	} else if (c == MANGLE_qual) {
-
 
739
		unsigned n;
-
 
740
		s++;
-
 
741
		n = unmangle_digit(&s);
-
 
742
		while (n) {
-
 
743
			NAMESPACE pns;
-
 
744
			id = unmangle_nspace(&s, ns, 0);
-
 
745
			pns = find_namespace(id);
-
 
746
			if (!IS_NULL_nspace(pns)) {
-
 
747
				ns = pns;
-
 
748
			}
-
 
749
			n--;
-
 
750
		}
-
 
751
 
-
 
752
	} else if (c == MANGLE_template) {
-
 
753
		s++;
-
 
754
		id = unmangle_nspace(&s, ns, 0);
-
 
755
		if (!IS_NULL_id(id)) {
-
 
756
			LIST(TOKEN)args = unmangle_token_args(&s);
-
 
757
			TYPE t = make_dummy_class(id, args, btype_lang);
-
 
758
			CLASS_TYPE ct = DEREF_ctype(type_compound_defn(t));
-
 
759
			id = DEREF_id(ctype_name(ct));
578
		}
760
		}
579
		n-- ;
-
 
580
	    }
-
 
581
	    *q = 0 ;
-
 
582
	    nm = lookup_name ( p, hash ( p ), ext, lex_identifier ) ;
-
 
583
	    if ( var ) {
-
 
584
		t = type_sint ;
-
 
585
		MAKE_id_variable ( nm, dspec_extern, ns, crt_loc, t, id ) ;
-
 
586
	    } else {
-
 
587
		id = make_class ( ns, nm, btype_lang, dspec_extern, t, t ) ;
-
 
588
	    }
-
 
589
	}
-
 
590
 
761
 
591
    } else if ( c == MANGLE_qual ) {
-
 
592
	unsigned n ;
-
 
593
	s++ ;
-
 
594
	n = unmangle_digit ( &s ) ;
-
 
595
	while ( n ) {
-
 
596
	    NAMESPACE pns ;
-
 
597
	    id = unmangle_nspace ( &s, ns, 0 ) ;
-
 
598
	    pns = find_namespace ( id ) ;
-
 
599
	    if ( !IS_NULL_nspace ( pns ) ) ns = pns ;
-
 
600
	    n-- ;
-
 
601
	}
-
 
602
 
-
 
603
    } else if ( c == MANGLE_template ) {
-
 
604
	s++ ;
-
 
605
	id = unmangle_nspace ( &s, ns, 0 ) ;
-
 
606
	if ( !IS_NULL_id ( id ) ) {
-
 
607
	    LIST ( TOKEN ) args = unmangle_token_args ( &s ) ;
-
 
608
	    TYPE t = make_dummy_class ( id, args, btype_lang ) ;
-
 
609
	    CLASS_TYPE ct = DEREF_ctype ( type_compound_defn ( t ) ) ;
-
 
610
	    id = DEREF_id ( ctype_name ( ct ) ) ;
-
 
611
	}
-
 
612
 
-
 
613
    } else if ( c == MANGLE_templ_param ) {
762
	} else if (c == MANGLE_templ_param) {
614
	TOKEN tok ;
763
		TOKEN tok;
615
	s++ ;
764
		s++;
616
	tok = find_token_arg ( &s ) ;
765
		tok = find_token_arg(&s);
617
	if ( !IS_NULL_tok ( tok ) && IS_tok_type ( tok ) ) {
766
		if (!IS_NULL_tok(tok) && IS_tok_type(tok)) {
618
	    TYPE t = DEREF_type ( tok_type_value ( tok ) ) ;
767
			TYPE t = DEREF_type(tok_type_value(tok));
619
	    if ( !IS_NULL_type ( t ) && IS_type_compound ( t ) ) {
768
			if (!IS_NULL_type(t) && IS_type_compound(t)) {
-
 
769
				CLASS_TYPE ct =
620
		CLASS_TYPE ct = DEREF_ctype ( type_compound_defn ( t ) ) ;
770
				    DEREF_ctype(type_compound_defn(t));
621
		id = DEREF_id ( ctype_name ( ct ) ) ;
771
				id = DEREF_id(ctype_name(ct));
622
	    }
772
			}
623
	}
773
		}
624
    }
774
	}
625
    *ps = s ;
775
	*ps = s;
626
    return ( id ) ;
776
	return (id);
627
}
777
}
628
 
778
 
629
 
779
 
630
/*
780
/*
631
    UNMANGLE A TOKEN ARGUMENT
781
    UNMANGLE A TOKEN ARGUMENT
632
 
782
 
633
    This routine unmangles a token or template argument from the string
783
    This routine unmangles a token or template argument from the string
634
    pointed to by ps.
784
    pointed to by ps.
635
*/
785
*/
636
 
786
 
637
static TOKEN unmangle_token_arg
787
static TOKEN
638
    PROTO_N ( ( ps ) )
-
 
639
    PROTO_T ( string *ps )
788
unmangle_token_arg(string *ps)
640
{
789
{
641
    TOKEN tok = NULL_tok ;
790
	TOKEN tok = NULL_tok;
642
    string s = *ps ;
791
	string s = *ps;
643
    character c = *s ;
792
	character c = *s;
644
    switch ( c ) {
793
	switch (c) {
645
	case MANGLE_nat : {
794
	case MANGLE_nat: {
646
	    /* Integer constant tokens */
795
		/* Integer constant tokens */
647
	    NAT n ;
796
		NAT n;
648
	    s++ ;
797
		s++;
649
	    n = unmangle_nat ( &s ) ;
798
		n = unmangle_nat(&s);
650
	    if ( !IS_NULL_nat ( n ) ) {
799
		if (!IS_NULL_nat(n)) {
651
		MAKE_tok_nat ( n, tok ) ;
800
			MAKE_tok_nat(n, tok);
-
 
801
		}
-
 
802
		break;
-
 
803
	}
-
 
804
	case MANGLE_stmt: {
-
 
805
		/* Statement tokens */
-
 
806
		EXP e;
-
 
807
		s++;
-
 
808
		e = unmangle_exp(&s, type_void);
-
 
809
		if (!IS_NULL_exp(e)) {
-
 
810
			MAKE_tok_stmt(e, tok);
652
	    }
811
		}
-
 
812
		break;
-
 
813
	}
-
 
814
	case MANGLE_type: {
-
 
815
		/* Type tokens */
-
 
816
		TYPE t;
-
 
817
		s++;
-
 
818
		t = unmangle_type(&s, cv_none, btype_none, 1);
-
 
819
		MAKE_tok_type(btype_none, t, tok);
653
	    break ;
820
		break;
654
	}
821
	}
655
	case MANGLE_stmt : {
822
	default: {
656
	    /* Statement tokens */
823
		/* Expression tokens */
657
	    EXP e ;
824
		TYPE t = unmangle_type(&s, cv_none, btype_none, 1);
658
	    s++ ;
-
 
659
	    e = unmangle_exp ( &s, type_void ) ;
825
		EXP e = unmangle_exp(&s, t);
660
	    if ( !IS_NULL_exp ( e ) ) {
826
		if (!IS_NULL_exp(e)) {
661
		MAKE_tok_stmt ( e, tok ) ;
827
			MAKE_tok_exp(t, 0, e, tok);
662
	    }
828
		}
663
	    break ;
829
		break;
664
	}
830
	}
665
	case MANGLE_type : {
-
 
666
	    /* Type tokens */
-
 
667
	    TYPE t ;
-
 
668
	    s++ ;
-
 
669
	    t = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
-
 
670
	    MAKE_tok_type ( btype_none, t, tok ) ;
-
 
671
	    break ;
-
 
672
	}
831
	}
673
	default : {
-
 
674
	    /* Expression tokens */
-
 
675
	    TYPE t = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
-
 
676
	    EXP e = unmangle_exp ( &s, t ) ;
-
 
677
	    if ( !IS_NULL_exp ( e ) ) {
-
 
678
		MAKE_tok_exp ( t, 0, e, tok ) ;
-
 
679
	    }
-
 
680
	    break ;
-
 
681
	}
-
 
682
    }
-
 
683
    *ps = s ;
832
	*ps = s;
684
    return ( tok ) ;
833
	return (tok);
685
}
834
}
686
 
835
 
687
 
836
 
688
/*
837
/*
689
    UNMANGLE A LIST OF TOKEN ARGUMENTS
838
    UNMANGLE A LIST OF TOKEN ARGUMENTS
690
 
839
 
691
    This routine unmangles a list of token or template arguments from the
840
    This routine unmangles a list of token or template arguments from the
692
    string pointed to by ps.
841
    string pointed to by ps.
693
*/
842
*/
694
 
843
 
695
static LIST ( TOKEN ) unmangle_token_args
844
static LIST(TOKEN)
696
    PROTO_N ( ( ps ) )
-
 
697
    PROTO_T ( string *ps )
845
unmangle_token_args(string *ps)
698
{
846
{
699
    string s = *ps ;
847
	string s = *ps;
700
    unsigned n = unmangle_digit ( &s ) ;
848
	unsigned n = unmangle_digit(&s);
701
    LIST ( TOKEN ) args = NULL_list ( TOKEN ) ;
849
	LIST(TOKEN)args = NULL_list(TOKEN);
702
    while ( n ) {
850
	while (n) {
703
	TOKEN tok = unmangle_token_arg ( &s ) ;
851
		TOKEN tok = unmangle_token_arg(&s);
704
	if ( !IS_NULL_tok ( tok ) ) {
852
		if (!IS_NULL_tok(tok)) {
705
	    CONS_tok ( tok, args, args ) ;
853
			CONS_tok(tok, args, args);
-
 
854
		}
-
 
855
		if (*s == 0) {
-
 
856
			break;
-
 
857
		}
-
 
858
		n--;
706
	}
859
	}
707
	if ( *s == 0 ) break ;
-
 
708
	n-- ;
-
 
709
    }
-
 
710
    args = REVERSE_list ( args ) ;
860
	args = REVERSE_list(args);
711
    *ps = s ;
861
	*ps = s;
712
    return ( args ) ;
862
	return (args);
713
}
863
}
714
 
864
 
715
 
865
 
716
/*
866
/*
717
    FIND A TOKEN ARGUMENT VALUE
867
    FIND A TOKEN ARGUMENT VALUE
718
 
868
 
719
    This routine returns the an argument from the current argument list.
869
    This routine returns the an argument from the current argument list.
720
    The arguments are numbered from zero.
870
    The arguments are numbered from zero.
721
*/
871
*/
722
 
872
 
723
static TOKEN find_token_arg
873
static TOKEN
724
    PROTO_N ( ( ps ) )
-
 
725
    PROTO_T ( string *ps )
874
find_token_arg(string *ps)
726
{
875
{
727
    unsigned n = unmangle_digit ( ps ) ;
876
	unsigned n = unmangle_digit(ps);
728
    LIST ( TOKEN ) args = crt_unmangle_args ;
877
	LIST(TOKEN)args = crt_unmangle_args;
729
    while ( !IS_NULL_list ( args ) ) {
878
	while (!IS_NULL_list(args)) {
730
	if ( n == 0 ) {
879
		if (n == 0) {
731
	    /* Token argument found */
880
			/* Token argument found */
732
	    TOKEN arg = DEREF_tok ( HEAD_list ( args ) ) ;
881
			TOKEN arg = DEREF_tok(HEAD_list(args));
733
	    return ( arg ) ;
882
			return (arg);
734
	}
883
		}
735
	n-- ;
884
		n--;
736
	args = TAIL_list ( args ) ;
885
		args = TAIL_list(args);
737
    }
886
	}
738
    return ( NULL_tok ) ;
887
	return (NULL_tok);
739
}
888
}
740
 
889
 
741
 
890
 
742
/*
891
/*
743
    FIND A FUNCTION PARAMETER TYPE
892
    FIND A FUNCTION PARAMETER TYPE
744
 
893
 
745
    This routine returns the mth parameter type from the members mem.
894
    This routine returns the mth parameter type from the members mem.
746
    The parameters are numbered from one, with n giving the total number
895
    The parameters are numbered from one, with n giving the total number
747
    of parameters.
896
    of parameters.
748
*/
897
*/
749
 
898
 
750
static TYPE unmangle_param
899
static TYPE
751
    PROTO_N ( ( m, n, mem ) )
-
 
752
    PROTO_T ( unsigned m X unsigned n X MEMBER mem )
900
unmangle_param(unsigned m, unsigned n, MEMBER mem)
753
{
901
{
754
    while ( !IS_NULL_member ( mem ) ) {
902
	while (!IS_NULL_member(mem)) {
755
	IDENTIFIER id = DEREF_id ( member_id ( mem ) ) ;
903
		IDENTIFIER id = DEREF_id(member_id(mem));
756
	if ( !IS_NULL_id ( id ) && IS_id_parameter ( id ) ) {
904
		if (!IS_NULL_id(id) && IS_id_parameter(id)) {
757
	    if ( m == n ) {
905
			if (m == n) {
758
		/* Parameter type found */
906
				/* Parameter type found */
759
		TYPE t = DEREF_type ( id_parameter_type ( id ) ) ;
907
				TYPE t = DEREF_type(id_parameter_type(id));
760
		return ( t ) ;
908
				return (t);
761
	    }
909
			}
762
	    m++ ;
910
			m++;
763
	}
911
		}
764
	mem = DEREF_member ( member_next ( mem ) ) ;
912
		mem = DEREF_member(member_next(mem));
765
    }
913
	}
766
    return ( type_error ) ;
914
	return (type_error);
767
}
915
}
768
 
916
 
769
 
917
 
770
/*
918
/*
771
    UNMANGLE A FUNCTION TYPE
919
    UNMANGLE A FUNCTION TYPE
772
 
920
 
773
    This routine unmangles a function type from the string pointed to
921
    This routine unmangles a function type from the string pointed to
774
    by ps.
922
    by ps.
775
*/
923
*/
776
 
924
 
777
static TYPE unmangle_func
925
static TYPE
778
    PROTO_N ( ( ps, cv, ret ) )
-
 
779
    PROTO_T ( string *ps X CV_SPEC cv X int ret )
926
unmangle_func(string *ps, CV_SPEC cv, int ret)
780
{
-
 
781
    TYPE t ;
-
 
782
    string s = *ps ;
-
 
783
    character c = *s ;
-
 
784
    if ( c == MANGLE_const ) {
-
 
785
	/* Const member function type */
-
 
786
	s++ ;
-
 
787
	cv |= cv_const ;
-
 
788
	t = unmangle_func ( &s, cv, ret ) ;
-
 
789
 
-
 
790
    } else if ( c == MANGLE_volatile ) {
-
 
791
	/* Volatile member function type */
-
 
792
	s++ ;
-
 
793
	cv |= cv_volatile ;
-
 
794
	t = unmangle_func ( &s, cv, ret ) ;
-
 
795
 
-
 
796
    } else if ( c == MANGLE_c_lang ) {
-
 
797
	/* C linkage function type */
-
 
798
	s++ ;
-
 
799
	cv |= cv_c ;
-
 
800
	t = unmangle_func ( &s, cv, ret ) ;
-
 
801
 
-
 
802
    } else {
-
 
803
	/* Read list of parameter types */
-
 
804
	TYPE t1 ;
-
 
805
	MEMBER mem ;
-
 
806
	NAMESPACE ns ;
-
 
807
	unsigned npars = 0 ;
-
 
808
	int ell = FUNC_NONE ;
-
 
809
	begin_param ( NULL_id ) ;
-
 
810
	ns = crt_namespace ;
-
 
811
	for ( ; ; ) {
-
 
812
	    /* Read parameter types */
-
 
813
	    unsigned m ;
-
 
814
	    unsigned n = 1 ;
-
 
815
	    c = *s ;
-
 
816
	    if ( c == 0 ) {
-
 
817
		break ;
-
 
818
	    } else if ( c == MANGLE_ellipsis ) {
-
 
819
		/* Ellipsis */
-
 
820
		s++ ;
-
 
821
		ell = FUNC_ELLIPSIS ;
-
 
822
		break ;
-
 
823
	    } else if ( c == MANGLE_repeat ) {
-
 
824
		/* Repeated parameter */
-
 
825
		s++ ;
-
 
826
		m = unmangle_digit ( &s ) ;
-
 
827
		mem = DEREF_member ( nspace_last ( ns ) ) ;
-
 
828
		t1 = unmangle_param ( m, npars, mem ) ;
-
 
829
	    } else if ( c == MANGLE_multi ) {
-
 
830
		/* Multiply repeated parameter */
-
 
831
		s++ ;
-
 
832
		n = unmangle_digit ( &s ) ;
-
 
833
		m = unmangle_no ( &s, 1 ) ;
-
 
834
		mem = DEREF_member ( nspace_last ( ns ) ) ;
-
 
835
		t1 = unmangle_param ( m, npars, mem ) ;
-
 
836
	    } else {
-
 
837
		/* Simple parameter type */
-
 
838
		t1 = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
-
 
839
		if ( IS_type_error ( t1 ) ) break ;
-
 
840
	    }
-
 
841
	    while ( n ) {
-
 
842
		/* Declare parameters */
-
 
843
		DECL_SPEC ds = dspec_none ;
-
 
844
		HASHID nm = lookup_anon () ;
-
 
845
		IDENTIFIER pid = DEREF_id ( hashid_id ( nm ) ) ;
-
 
846
		pid = make_param_decl ( ds, t1, pid, CONTEXT_PARAMETER ) ;
-
 
847
		init_param ( pid, NULL_exp ) ;
-
 
848
		npars++ ;
-
 
849
		n-- ;
-
 
850
	    }
-
 
851
	}
-
 
852
	t = make_func_type ( dummy_ret_type, ell, cv, empty_type_set ) ;
-
 
853
	end_param () ;
-
 
854
	if ( ret ) {
-
 
855
	    /* Read return type */
-
 
856
	    c = *( s++ ) ;
-
 
857
	    if ( c == MANGLE_sep ) {
-
 
858
		t1 = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
-
 
859
	    } else {
-
 
860
		t1 = type_error ;
-
 
861
		s-- ;
-
 
862
	    }
-
 
863
	    COPY_type ( type_func_ret ( t ), NULL_type ) ;
-
 
864
	    t = inject_pre_type ( t, t1, 0 ) ;
-
 
865
	}
-
 
866
    }
-
 
867
    *ps = s ;
-
 
868
    return ( t ) ;
-
 
869
}
-
 
870
 
-
 
871
 
-
 
872
/*
-
 
873
    UNMANGLE A TYPE
-
 
874
 
-
 
875
    This routine unmangles a type from the string pointed to by ps.
-
 
876
*/
-
 
877
 
-
 
878
static TYPE unmangle_type
-
 
879
    PROTO_N ( ( ps, cv, bt, ret ) )
-
 
880
    PROTO_T ( string *ps X CV_SPEC cv X BASE_TYPE bt X int ret )
-
 
881
{
927
{
882
    TYPE t ;
928
	TYPE t;
883
    string s = *ps ;
929
	string s = *ps;
884
    character c = *( s++ ) ;
930
	character c = *s;
885
    switch ( c ) {
931
	if (c == MANGLE_const) {
886
 
-
 
887
	case MANGLE_char : t = make_base_type ( bt | btype_char ) ; break ;
932
		/* Const member function type */
-
 
933
		s++;
888
	case MANGLE_short : t = make_base_type ( bt | btype_short ) ; break ;
934
		cv |= cv_const;
889
	case MANGLE_int : t = make_base_type ( bt | btype_int ) ; break ;
935
		t = unmangle_func(&s, cv, ret);
890
	case MANGLE_long : t = make_base_type ( bt | btype_long ) ; break ;
936
	} else if (c == MANGLE_volatile) {
891
	case MANGLE_llong : t = make_base_type ( bt | btype_llong ) ; break ;
937
		/* Volatile member function type */
892
 
938
		s++;
893
	case MANGLE_float : t = type_float ; break ;
939
		cv |= cv_volatile;
894
	case MANGLE_double : t = type_double ; break ;
940
		t = unmangle_func(&s, cv, ret);
895
	case MANGLE_ldouble : t = type_ldouble ; break ;
941
	} else if (c == MANGLE_c_lang) {
896
	case MANGLE_void : t = type_void ; break ;
942
		/* C linkage function type */
-
 
943
		s++;
-
 
944
		cv |= cv_c;
897
	case MANGLE_bottom : t = type_bottom ; break ;
945
		t = unmangle_func(&s, cv, ret);
-
 
946
	} else {
898
	case MANGLE_bool : t = type_bool ; break ;
947
		/* Read list of parameter types */
-
 
948
		TYPE t1;
-
 
949
		MEMBER mem;
-
 
950
		NAMESPACE ns;
899
	case MANGLE_ptrdiff_t : t = type_ptrdiff_t ; break ;
951
		unsigned npars = 0;
900
	case MANGLE_size_t : t = type_size_t ; break ;
952
		int ell = FUNC_NONE;
901
	case MANGLE_wchar_t : t = type_wchar_t ; break ;
953
		begin_param(NULL_id);
902
 
-
 
903
	case MANGLE_signed : {
954
		ns = crt_namespace;
-
 
955
		for (;;) {
904
	    /* Signed types */
956
			/* Read parameter types */
905
	    bt |= btype_signed ;
957
			unsigned m;
906
	    t = unmangle_type ( &s, cv_none, bt, ret ) ;
958
			unsigned n = 1;
-
 
959
			c = *s;
-
 
960
			if (c == 0) {
907
	    break ;
961
				break;
-
 
962
			} else if (c == MANGLE_ellipsis) {
-
 
963
				/* Ellipsis */
908
	}
964
				s++;
-
 
965
				ell = FUNC_ELLIPSIS;
909
 
966
				break;
910
	case MANGLE_unsigned : {
967
			} else if (c == MANGLE_repeat) {
911
	    /* Unsigned types */
968
				/* Repeated parameter */
-
 
969
				s++;
912
	    bt |= btype_unsigned ;
970
				m = unmangle_digit(&s);
-
 
971
				mem = DEREF_member(nspace_last(ns));
913
	    t = unmangle_type ( &s, cv_none, bt, ret ) ;
972
				t1 = unmangle_param(m, npars, mem);
914
	    break ;
973
			} else if (c == MANGLE_multi) {
-
 
974
				/* Multiply repeated parameter */
915
	}
975
				s++;
916
 
-
 
917
	case MANGLE_const : {
976
				n = unmangle_digit(&s);
918
	    /* Const types */
977
				m = unmangle_no(&s, 1);
919
	    cv |= cv_const ;
978
				mem = DEREF_member(nspace_last(ns));
920
	    t = unmangle_type ( &s, cv, bt, ret ) ;
979
				t1 = unmangle_param(m, npars, mem);
921
	    cv = cv_none ;
980
			} else {
-
 
981
				/* Simple parameter type */
-
 
982
				t1 = unmangle_type(&s, cv_none, btype_none, 1);
922
	    break ;
983
				if (IS_type_error(t1))break;
923
	}
984
			}
924
 
-
 
925
	case MANGLE_volatile : {
985
			while (n) {
926
	    /* Volatile types */
986
				/* Declare parameters */
-
 
987
				DECL_SPEC ds = dspec_none;
927
	    cv |= cv_volatile ;
988
				HASHID nm = lookup_anon();
-
 
989
				IDENTIFIER pid = DEREF_id(hashid_id(nm));
928
	    t = unmangle_type ( &s, cv, bt, ret ) ;
990
				pid = make_param_decl(ds, t1, pid,
929
	    cv = cv_none ;
991
						      CONTEXT_PARAMETER);
-
 
992
				init_param(pid, NULL_exp);
930
	    break ;
993
				npars++;
-
 
994
				n--;
931
	}
995
			}
932
 
996
		}
-
 
997
		t = make_func_type(dummy_ret_type, ell, cv, empty_type_set);
-
 
998
		end_param();
933
	case MANGLE_ptr : {
999
		if (ret) {
934
	    /* Pointer types */
1000
			/* Read return type */
-
 
1001
			c = *(s++);
-
 
1002
			if (c == MANGLE_sep) {
935
	    TYPE t1 = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
1003
				t1 = unmangle_type(&s, cv_none, btype_none, 1);
-
 
1004
			} else {
-
 
1005
				t1 = type_error;
-
 
1006
				s--;
-
 
1007
			}
936
	    MAKE_type_ptr ( cv, NULL_type, t ) ;
1008
			COPY_type(type_func_ret(t), NULL_type);
937
	    t = inject_pre_type ( t, t1, 0 ) ;
1009
			t = inject_pre_type(t, t1, 0);
938
	    cv = cv_none ;
-
 
939
	    break ;
1010
		}
940
	}
1011
	}
-
 
1012
	*ps = s;
-
 
1013
	return (t);
-
 
1014
}
941
 
1015
 
942
	case MANGLE_ref : {
-
 
943
	    /* Reference types */
-
 
944
	    TYPE t1 = unmangle_type ( &s, cv, btype_none, 1 ) ;
-
 
945
	    MAKE_type_ref ( cv_none, NULL_type, t ) ;
-
 
946
	    t = inject_pre_type ( t, t1, 0 ) ;
-
 
947
	    cv = cv_none ;
-
 
948
	    break ;
-
 
949
	}
-
 
950
 
-
 
951
	case MANGLE_ptr_mem : {
-
 
952
	    /* Pointer to member types */
-
 
953
	    TYPE t1 = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
-
 
954
	    TYPE t2 = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
-
 
955
	    if ( IS_type_compound ( t1 ) ) {
-
 
956
		CLASS_TYPE c1 = DEREF_ctype ( type_compound_defn ( t1 ) ) ;
-
 
957
		MAKE_type_ptr_mem ( cv, c1, NULL_type, t ) ;
-
 
958
	    } else {
-
 
959
		report ( crt_loc, ERR_dcl_mptr_class ( t1 ) ) ;
-
 
960
		MAKE_type_ptr ( cv, NULL_type, t ) ;
-
 
961
	    }
-
 
962
	    t = inject_pre_type ( t, t2, 0 ) ;
-
 
963
	    cv = cv_none ;
-
 
964
	    break ;
-
 
965
	}
-
 
966
 
-
 
967
	case MANGLE_func : {
-
 
968
	    /* Function types */
-
 
969
	    t = unmangle_func ( &s, cv, ret ) ;
-
 
970
	    cv = cv_none ;
-
 
971
	    break ;
-
 
972
	}
-
 
973
 
-
 
974
	case MANGLE_array : {
-
 
975
	    /* Array types */
-
 
976
	    NAT n = unmangle_nat ( &s ) ;
-
 
977
	    TYPE t1 = unmangle_type ( &s, cv, btype_none, 1 ) ;
-
 
978
	    n = check_array_dim ( n ) ;
-
 
979
	    MAKE_type_array ( cv_none, NULL_type, n, t ) ;
-
 
980
	    t = inject_pre_type ( t, t1, 0 ) ;
-
 
981
	    cv = cv_none ;
-
 
982
	    break ;
-
 
983
	}
-
 
984
 
-
 
985
	case MANGLE_bitfield : {
-
 
986
	    /* Bitfield types */
-
 
987
	    TYPE t1 ;
-
 
988
	    NAT n = unmangle_nat ( &s ) ;
-
 
989
	    BASE_TYPE b1 = btype_named ;
-
 
990
	    if ( *s == MANGLE_signed ) b1 |= btype_signed ;
-
 
991
	    t1 = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
-
 
992
	    b1 = get_bitfield_rep ( t1, b1 ) ;
-
 
993
	    t = check_bitfield_type ( cv, t1, b1, n, 0 ) ;
-
 
994
	    cv = cv_none ;
-
 
995
	    break ;
-
 
996
	}
-
 
997
 
-
 
998
	case MANGLE_template : {
-
 
999
	    /* Template class types */
-
 
1000
	    IDENTIFIER id = unmangle_nspace ( &s, global_namespace, 0 ) ;
-
 
1001
	    if ( IS_NULL_id ( id ) ) {
-
 
1002
		t = type_error ;
-
 
1003
	    } else {
-
 
1004
		LIST ( TOKEN ) args = unmangle_token_args ( &s ) ;
-
 
1005
		MAKE_type_token ( cv, id, args, t ) ;
-
 
1006
		cv = cv_none ;
-
 
1007
	    }
-
 
1008
	    break ;
-
 
1009
	}
-
 
1010
 
-
 
1011
	case MANGLE_templ_param : {
-
 
1012
	    /* Template parameter types */
-
 
1013
	    TOKEN tok = find_token_arg ( &s ) ;
-
 
1014
	    if ( !IS_NULL_tok ( tok ) && IS_tok_type ( tok ) ) {
-
 
1015
		t = DEREF_type ( tok_type_value ( tok ) ) ;
-
 
1016
	    } else {
-
 
1017
		t = type_error ;
-
 
1018
	    }
-
 
1019
	    break ;
-
 
1020
	}
-
 
1021
 
-
 
1022
	case MANGLE_promote : {
-
 
1023
	    /* Promotion types */
-
 
1024
	    TYPE t1 = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
-
 
1025
	    t = promote_type ( t1 ) ;
-
 
1026
	    break ;
-
 
1027
	}
-
 
1028
 
-
 
1029
	case MANGLE_arith : {
-
 
1030
	    /* Arithmetic types */
-
 
1031
	    TYPE t1 = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
-
 
1032
	    TYPE t2 = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
-
 
1033
	    t = arith_type ( t1, t2, NULL_exp, NULL_exp ) ;
-
 
1034
	    break ;
-
 
1035
	}
-
 
1036
 
-
 
1037
	case MANGLE_literal : {
-
 
1038
	    /* Literal types */
-
 
1039
	    NAT n ;
-
 
1040
	    int fit = 0 ;
-
 
1041
	    int form = BASE_DECIMAL ;
-
 
1042
	    int suff = SUFFIX_NONE ;
-
 
1043
	    c = *s ;
-
 
1044
	    if ( c == MANGLE_octal ) {
-
 
1045
		form = BASE_OCTAL ;
-
 
1046
		c = *( ++s ) ;
-
 
1047
	    } else if ( c == MANGLE_hex ) {
-
 
1048
		form = BASE_HEXADECIMAL ;
-
 
1049
		c = *( ++s ) ;
-
 
1050
	    }
-
 
1051
	    if ( c == MANGLE_unsigned ) {
-
 
1052
		suff |= SUFFIX_U ;
-
 
1053
		c = *( ++s ) ;
-
 
1054
	    }
-
 
1055
	    if ( c == MANGLE_long ) {
-
 
1056
		suff |= SUFFIX_L ;
-
 
1057
		c = *( ++s ) ;
-
 
1058
	    }
-
 
1059
	    if ( c == MANGLE_llong ) {
-
 
1060
		suff |= SUFFIX_LL ;
-
 
1061
		s++ ;
-
 
1062
	    }
-
 
1063
	    n = unmangle_nat ( &s ) ;
-
 
1064
	    if ( IS_NULL_nat ( n ) ) n = small_nat [0] ;
-
 
1065
	    t = find_literal_type ( n, form, suff, NULL_string, &fit ) ;
-
 
1066
	    break ;
-
 
1067
	}
-
 
1068
 
-
 
1069
	case MANGLE_self : {
-
 
1070
	    /* Parent class type */
-
 
1071
	    IDENTIFIER self = crt_unmangle_class ;
-
 
1072
	    if ( IS_NULL_id ( self ) ) {
-
 
1073
		t = type_error ;
-
 
1074
	    } else {
-
 
1075
		t = DEREF_type ( id_class_name_etc_defn ( self ) ) ;
-
 
1076
	    }
-
 
1077
	    break ;
-
 
1078
	}
-
 
1079
 
-
 
1080
	case char_zero : case char_one : case char_two :
-
 
1081
	case char_three : case char_four : case char_five :
-
 
1082
	case char_six : case char_seven : case char_eight :
-
 
1083
	case char_nine : case MANGLE_qual : {
-
 
1084
	    /* Named types */
-
 
1085
	    IDENTIFIER id ;
-
 
1086
	    s-- ;
-
 
1087
	    id = unmangle_nspace ( &s, global_namespace, 0 ) ;
-
 
1088
	    if ( IS_NULL_id ( id ) ) {
-
 
1089
		t = type_error ;
-
 
1090
	    } else {
-
 
1091
		t = DEREF_type ( id_class_name_etc_defn ( id ) ) ;
-
 
1092
	    }
-
 
1093
	    break ;
-
 
1094
	}
-
 
1095
 
1016
 
1096
	default : {
-
 
1097
	    /* Invalid mangled types */
-
 
1098
	    if ( bt == btype_none && cv == cv_none ) {
-
 
1099
		t = type_error ;
-
 
1100
	    } else {
-
 
1101
		t = make_base_type ( bt | btype_int ) ;
-
 
1102
	    }
-
 
1103
	    s-- ;
-
 
1104
	    break ;
-
 
1105
	}
-
 
1106
    }
-
 
1107
    if ( cv ) t = qualify_type ( t, cv, 0 ) ;
-
 
1108
    *ps = s ;
-
 
1109
    return ( t ) ;
-
 
1110
}
-
 
1111
 
-
 
1112
 
-
 
1113
/*
1017
/*
1114
    UNMANGLE AN IDENTIFIER NAME
1018
    UNMANGLE A TYPE
1115
 
1019
 
1116
    This routine unmangles the identifier s into the buffer bf.
1020
    This routine unmangles a type from the string pointed to by ps.
1117
*/
1021
*/
1118
 
1022
 
1119
static string unmangle_name
1023
static TYPE
1120
    PROTO_N ( ( s, bf ) )
-
 
1121
    PROTO_T ( string s X BUFFER *bf )
1024
unmangle_type(string *ps, CV_SPEC cv, BASE_TYPE bt, int ret)
1122
{
1025
{
-
 
1026
	TYPE t;
1123
    int func = 0 ;
1027
	string s = *ps;
-
 
1028
	character c = *(s++);
-
 
1029
	switch (c) {
-
 
1030
 
-
 
1031
	case MANGLE_char:
1124
    int op = lex_identifier ;
1032
		t = make_base_type(bt | btype_char);
-
 
1033
		break;
-
 
1034
	case MANGLE_short:
-
 
1035
		t = make_base_type(bt | btype_short);
-
 
1036
		break;
-
 
1037
	case MANGLE_int:
1125
    IDENTIFIER id = NULL_id ;
1038
		t = make_base_type(bt | btype_int);
-
 
1039
		break;
-
 
1040
	case MANGLE_long:
-
 
1041
		t = make_base_type(bt | btype_long);
-
 
1042
		break;
-
 
1043
	case MANGLE_llong:
-
 
1044
		t = make_base_type(bt | btype_llong);
-
 
1045
		break;
-
 
1046
	case MANGLE_float:
-
 
1047
		t = type_float;
-
 
1048
		break;
-
 
1049
	case MANGLE_double:
-
 
1050
		t = type_double;
-
 
1051
		break;
-
 
1052
	case MANGLE_ldouble:
-
 
1053
		t = type_ldouble;
-
 
1054
		break;
-
 
1055
	case MANGLE_void:
-
 
1056
		t = type_void;
-
 
1057
		break;
-
 
1058
	case MANGLE_bottom:
-
 
1059
		t = type_bottom;
-
 
1060
		break;
-
 
1061
	case MANGLE_bool:
-
 
1062
		t = type_bool;
-
 
1063
		break;
-
 
1064
	case MANGLE_ptrdiff_t:
-
 
1065
		t = type_ptrdiff_t;
-
 
1066
		break;
-
 
1067
	case MANGLE_size_t:
-
 
1068
		t = type_size_t;
-
 
1069
		break;
-
 
1070
	case MANGLE_wchar_t:
-
 
1071
		t = type_wchar_t;
-
 
1072
		break;
1126
    HASHID nm = NULL_hashid ;
1073
	case MANGLE_signed: {
-
 
1074
		/* Signed types */
-
 
1075
		bt |= btype_signed;
-
 
1076
		t = unmangle_type(&s, cv_none, bt, ret);
-
 
1077
		break;
1127
 
1078
	}
-
 
1079
	case MANGLE_unsigned: {
1128
    /* Check names beginning with '__' */
1080
		/* Unsigned types */
-
 
1081
		bt |= btype_unsigned;
1129
    if ( s [0] == '_' && s [1] == '_' ) {
1082
		t = unmangle_type(&s, cv_none, bt, ret);
-
 
1083
		break;
-
 
1084
	}
-
 
1085
	case MANGLE_const: {
1130
	string s0 = s + 2 ;
1086
		/* Const types */
-
 
1087
		cv |= cv_const;
1131
	op = unmangle_op ( &s0 ) ;
1088
		t = unmangle_type(&s, cv, bt, ret);
-
 
1089
		cv = cv_none;
-
 
1090
		break;
-
 
1091
	}
1132
	if ( op == lex_unknown ) {
1092
	case MANGLE_volatile: {
-
 
1093
		/* Volatile types */
1133
#if ( TDF_major < 4 )
1094
		cv |= cv_volatile;
-
 
1095
		t = unmangle_type(&s, cv, bt, ret);
-
 
1096
		cv = cv_none;
-
 
1097
		break;
-
 
1098
	}
-
 
1099
	case MANGLE_ptr: {
-
 
1100
		/* Pointer types */
1134
	    if ( ustrseq ( s, "__MAIN__" ) s = ustrlit ( "main" ) ;
1101
		TYPE t1 = unmangle_type(&s, cv_none, btype_none, 1);
-
 
1102
		MAKE_type_ptr(cv, NULL_type, t);
-
 
1103
		t = inject_pre_type(t, t1, 0);
-
 
1104
		cv = cv_none;
1135
#endif
1105
		break;
-
 
1106
	}
-
 
1107
	case MANGLE_ref: {
1136
	    bfputs ( bf, s ) ;
1108
		/* Reference types */
-
 
1109
		TYPE t1 = unmangle_type(&s, cv, btype_none, 1);
-
 
1110
		MAKE_type_ref(cv_none, NULL_type, t);
-
 
1111
		t = inject_pre_type(t, t1, 0);
-
 
1112
		cv = cv_none;
-
 
1113
		break;
-
 
1114
	}
-
 
1115
	case MANGLE_ptr_mem: {
-
 
1116
		/* Pointer to member types */
-
 
1117
		TYPE t1 = unmangle_type(&s, cv_none, btype_none, 1);
-
 
1118
		TYPE t2 = unmangle_type(&s, cv_none, btype_none, 1);
-
 
1119
		if (IS_type_compound(t1)) {
-
 
1120
			CLASS_TYPE c1 = DEREF_ctype(type_compound_defn(t1));
-
 
1121
			MAKE_type_ptr_mem(cv, c1, NULL_type, t);
-
 
1122
		} else {
-
 
1123
			report(crt_loc, ERR_dcl_mptr_class(t1));
-
 
1124
			MAKE_type_ptr(cv, NULL_type, t);
-
 
1125
		}
-
 
1126
		t = inject_pre_type(t, t2, 0);
-
 
1127
		cv = cv_none;
-
 
1128
		break;
-
 
1129
	}
-
 
1130
	case MANGLE_func: {
1137
	    return ( NULL ) ;
1131
		/* Function types */
-
 
1132
		t = unmangle_func(&s, cv, ret);
-
 
1133
		cv = cv_none;
-
 
1134
		break;
1138
	}
1135
	}
1139
	s = s0 ;
1136
	case MANGLE_array: {
1140
    }
1137
		/* Array types */
1141
 
-
 
-
 
1138
		NAT n = unmangle_nat(&s);
-
 
1139
		TYPE t1 = unmangle_type(&s, cv, btype_none, 1);
-
 
1140
		n = check_array_dim(n);
-
 
1141
		MAKE_type_array(cv_none, NULL_type, n, t);
1142
    /* Read identifier name */
1142
		t = inject_pre_type(t, t1, 0);
1143
    switch ( op ) {
1143
		cv = cv_none;
-
 
1144
		break;
1144
 
1145
	}
1145
	case lex_identifier : {
1146
	case MANGLE_bitfield: {
1146
	    /* Identifier name */
1147
		/* Bitfield types */
1147
	    character c ;
-
 
1148
	    int ext = 0 ;
1148
		TYPE t1;
1149
	    unsigned long h ;
1149
		NAT n = unmangle_nat(&s);
1150
	    BUFFER *tf = clear_buffer ( &token_buff, NIL ( FILE ) ) ;
-
 
1151
	    while ( c = *s, c != 0 ) {
1150
		BASE_TYPE b1 = btype_named;
1152
		if ( c == MANGLE_sep && s [1] == MANGLE_sep ) {
1151
		if (*s == MANGLE_signed) {
1153
		    c = s [2] ;
1152
			b1 |= btype_signed;
-
 
1153
		}
1154
		    if ( c == MANGLE_unicode4 ) {
1154
		t1 = unmangle_type(&s, cv_none, btype_none, 1);
1155
			bfputc ( tf, char_backslash ) ;
1155
		b1 = get_bitfield_rep(t1, b1);
-
 
1156
		t = check_bitfield_type(cv, t1, b1, n, 0);
1156
			c = char_u ;
1157
		cv = cv_none;
1157
			ext = 1 ;
1158
		break;
1158
			s += 2 ;
1159
	}
1159
		    } else if ( c == MANGLE_unicode8 ) {
1160
	case MANGLE_template: {
1160
			bfputc ( tf, char_backslash ) ;
1161
		/* Template class types */
1161
			c = char_U ;
1162
		IDENTIFIER id = unmangle_nspace(&s, global_namespace, 0);
1162
			ext = 1 ;
1163
		if (IS_NULL_id(id)) {
1163
			s += 2 ;
1164
			t = type_error;
1164
		    } else {
1165
		} else {
-
 
1166
			LIST(TOKEN)args = unmangle_token_args(&s);
1165
			break ;
1167
			MAKE_type_token(cv, id, args, t);
1166
		    }
1168
			cv = cv_none;
1167
		}
1169
		}
-
 
1170
		break;
-
 
1171
	}
-
 
1172
	case MANGLE_templ_param: {
-
 
1173
		/* Template parameter types */
-
 
1174
		TOKEN tok = find_token_arg(&s);
-
 
1175
		if (!IS_NULL_tok(tok) && IS_tok_type(tok)) {
-
 
1176
			t = DEREF_type(tok_type_value(tok));
-
 
1177
		} else {
-
 
1178
			t = type_error;
-
 
1179
		}
-
 
1180
		break;
-
 
1181
	}
-
 
1182
	case MANGLE_promote: {
-
 
1183
		/* Promotion types */
-
 
1184
		TYPE t1 = unmangle_type(&s, cv_none, btype_none, 1);
-
 
1185
		t = promote_type(t1);
-
 
1186
		break;
-
 
1187
	}
-
 
1188
	case MANGLE_arith: {
-
 
1189
		/* Arithmetic types */
-
 
1190
		TYPE t1 = unmangle_type(&s, cv_none, btype_none, 1);
-
 
1191
		TYPE t2 = unmangle_type(&s, cv_none, btype_none, 1);
-
 
1192
		t = arith_type(t1, t2, NULL_exp, NULL_exp);
-
 
1193
		break;
-
 
1194
	}
-
 
1195
	case MANGLE_literal: {
-
 
1196
		/* Literal types */
-
 
1197
		NAT n;
-
 
1198
		int fit = 0;
-
 
1199
		int form = BASE_DECIMAL;
-
 
1200
		int suff = SUFFIX_NONE;
-
 
1201
		c = *s;
-
 
1202
		if (c == MANGLE_octal) {
-
 
1203
			form = BASE_OCTAL;
-
 
1204
			c = *(++s);
-
 
1205
		} else if (c == MANGLE_hex) {
-
 
1206
			form = BASE_HEXADECIMAL;
-
 
1207
			c = *(++s);
-
 
1208
		}
1168
		bfputc ( tf, ( int ) c ) ;
1209
		if (c == MANGLE_unsigned) {
-
 
1210
			suff |= SUFFIX_U;
-
 
1211
			c = *(++s);
-
 
1212
		}
-
 
1213
		if (c == MANGLE_long) {
-
 
1214
			suff |= SUFFIX_L;
-
 
1215
			c = *(++s);
-
 
1216
		}
-
 
1217
		if (c == MANGLE_llong) {
-
 
1218
			suff |= SUFFIX_LL;
1169
		s++ ;
1219
			s++;
1170
	    }
1220
		}
-
 
1221
		n = unmangle_nat(&s);
1171
	    bfputc ( tf, 0 ) ;
1222
		if (IS_NULL_nat(n)) {
1172
	    h = hash ( tf->start ) ;
1223
			n = small_nat[0];
-
 
1224
		}
1173
	    nm = lookup_name ( tf->start, h, ext, lex_unknown ) ;
1225
		t = find_literal_type(n, form, suff, NULL_string, &fit);
-
 
1226
		break;
-
 
1227
	}
-
 
1228
	case MANGLE_self: {
-
 
1229
		/* Parent class type */
-
 
1230
		IDENTIFIER self = crt_unmangle_class;
-
 
1231
		if (IS_NULL_id(self)) {
-
 
1232
			t = type_error;
-
 
1233
		} else {
-
 
1234
			t = DEREF_type(id_class_name_etc_defn(self));
-
 
1235
		}
-
 
1236
		break;
-
 
1237
	}
-
 
1238
	case char_zero:
-
 
1239
	case char_one:
-
 
1240
	case char_two:
-
 
1241
	case char_three:
-
 
1242
	case char_four:
-
 
1243
	case char_five:
-
 
1244
	case char_six:
-
 
1245
	case char_seven:
-
 
1246
	case char_eight:
-
 
1247
	case char_nine:
-
 
1248
	case MANGLE_qual: {
-
 
1249
		/* Named types */
-
 
1250
		IDENTIFIER id;
-
 
1251
		s--;
-
 
1252
		id = unmangle_nspace(&s, global_namespace, 0);
-
 
1253
		if (IS_NULL_id(id)) {
-
 
1254
			t = type_error;
-
 
1255
		} else {
1174
	    id = DEREF_id ( hashid_id ( nm ) ) ;
1256
			t = DEREF_type(id_class_name_etc_defn(id));
-
 
1257
		}
1175
	    break ;
1258
		break;
1176
	}
1259
	}
1177
 
1260
 
1178
	case lex_type_Hname :
1261
	default: {
1179
	case lex_destructor_Hname : {
1262
		/* Invalid mangled types */
1180
	    /* Constructor and destructor names */
1263
		if (bt == btype_none && cv == cv_none) {
1181
	    func = 1 ;
1264
			t = type_error;
1182
	    break ;
1265
		} else {
1183
	}
-
 
1184
 
-
 
1185
	case lex_operator : {
-
 
1186
	    /* Conversion function name */
-
 
1187
	    TYPE t = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
1266
			t = make_base_type(bt | btype_int);
1188
	    nm = lookup_conv ( t ) ;
-
 
1189
	    id = DEREF_id ( hashid_id ( nm ) ) ;
-
 
1190
	    func = 1 ;
-
 
1191
	    break ;
-
 
1192
	}
1267
		}
1193
 
1268
		s--;
1194
	case lex_auto : {
1269
		break;
1195
	    /* Anonymous identifier */
-
 
1196
	    bfprintf ( bf, "<anon>" ) ;
-
 
1197
	    return ( NULL ) ;
-
 
1198
	}
1270
	}
1199
 
-
 
1200
	case lex_static : {
-
 
1201
	    /* Local static variable */
-
 
1202
	    bfprintf ( bf, "<static>" ) ;
-
 
1203
	    return ( NULL ) ;
-
 
1204
	}
1271
	}
-
 
1272
	if (cv) {
-
 
1273
		t = qualify_type(t, cv, 0);
-
 
1274
	}
-
 
1275
	*ps = s;
-
 
1276
	return (t);
-
 
1277
}
1205
 
1278
 
1206
	case lex_typeof : {
-
 
1207
	    /* Run-time type information */
-
 
1208
	    TYPE t = unmangle_type ( &s, cv_none, btype_none, 1 ) ;
-
 
1209
	    bfprintf ( bf, "typeid ( " ) ;
-
 
1210
	    IGNORE print_type ( t, bf, 0 ) ;
-
 
1211
	    bfprintf ( bf, " )" ) ;
-
 
1212
	    return ( s ) ;
-
 
1213
	}
-
 
1214
 
-
 
1215
	case lex_virtual : {
-
 
1216
	    /* Virtual function table */
-
 
1217
	    int sep = 0 ;
-
 
1218
	    bfprintf ( bf, "vtable ( " ) ;
-
 
1219
	    for ( ; ; ) {
-
 
1220
		id = unmangle_nspace ( &s, global_namespace, 0 ) ;
-
 
1221
		if ( IS_NULL_id ( id ) ) break ;
-
 
1222
		if ( sep ) bfprintf ( bf, "::" ) ;
-
 
1223
		IGNORE print_id_long ( id, qual_none, bf, 0 ) ;
-
 
1224
		sep = 1 ;
-
 
1225
	    }
-
 
1226
	    if ( !sep ) bfprintf ( bf, "<error>" ) ;
-
 
1227
	    bfprintf ( bf, " )" ) ;
-
 
1228
	    return ( s ) ;
-
 
1229
	}
-
 
1230
 
-
 
1231
	default : {
-
 
1232
	    /* Operator name */
-
 
1233
	    nm = lookup_op ( op ) ;
-
 
1234
	    if ( !IS_NULL_hashid ( nm ) ) {
-
 
1235
		id = DEREF_id ( hashid_id ( nm ) ) ;
-
 
1236
		func = 1 ;
-
 
1237
	    }
-
 
1238
	    break ;
-
 
1239
	}
-
 
1240
    }
-
 
1241
 
-
 
1242
    /* Unmangle identifier namespace and type */
-
 
1243
    if ( s [0] == MANGLE_sep && s [1] == MANGLE_sep ) {
-
 
1244
	TYPE t ;
-
 
1245
	string s0 = s + 2 ;
-
 
1246
	NAMESPACE pns = global_namespace ;
-
 
1247
	IDENTIFIER pid = unmangle_nspace ( &s0, pns, 0 ) ;
-
 
1248
	character c = *s0 ;
-
 
1249
	if ( c == MANGLE_func_templ ) {
-
 
1250
	    /* Allow for template functions */
-
 
1251
	    s0++ ;
-
 
1252
	    crt_unmangle_args = unmangle_token_args ( &s0 ) ;
-
 
1253
	    if ( *s0 == MANGLE_sep ) s0++ ;
-
 
1254
	}
-
 
1255
 
1279
 
-
 
1280
/*
-
 
1281
    UNMANGLE AN IDENTIFIER NAME
-
 
1282
 
-
 
1283
    This routine unmangles the identifier s into the buffer bf.
-
 
1284
*/
-
 
1285
 
-
 
1286
static string
-
 
1287
unmangle_name(string s, BUFFER *bf)
-
 
1288
{
-
 
1289
	int func = 0;
-
 
1290
	int op = lex_identifier;
-
 
1291
	IDENTIFIER id = NULL_id;
-
 
1292
	HASHID nm = NULL_hashid;
-
 
1293
 
-
 
1294
	/* Check names beginning with '__' */
-
 
1295
	if (s[0] == '_' && s[1] == '_') {
-
 
1296
		string s0 = s + 2;
-
 
1297
		op = unmangle_op(&s0);
-
 
1298
		if (op == lex_unknown) {
-
 
1299
#if (TDF_major < 4)
-
 
1300
			if (ustrseq(s, "__MAIN__")) {
-
 
1301
				s = ustrlit("main");
-
 
1302
			}
-
 
1303
#endif
-
 
1304
			bfputs(bf, s);
-
 
1305
			return (NULL);
-
 
1306
		}
-
 
1307
		s = s0;
-
 
1308
	}
-
 
1309
 
-
 
1310
	/* Read identifier name */
-
 
1311
	switch (op) {
-
 
1312
	case lex_identifier: {
-
 
1313
		/* Identifier name */
-
 
1314
		character c;
-
 
1315
		int ext = 0;
-
 
1316
		unsigned long h;
-
 
1317
		BUFFER *tf = clear_buffer(&token_buff, NIL(FILE));
-
 
1318
		while (c = *s, c != 0) {
-
 
1319
			if (c == MANGLE_sep && s[1] == MANGLE_sep) {
-
 
1320
				c = s[2];
-
 
1321
				if (c == MANGLE_unicode4) {
-
 
1322
					bfputc(tf, char_backslash);
-
 
1323
					c = char_u;
-
 
1324
					ext = 1;
-
 
1325
					s += 2;
-
 
1326
				} else if (c == MANGLE_unicode8) {
-
 
1327
					bfputc(tf, char_backslash);
-
 
1328
					c = char_U;
-
 
1329
					ext = 1;
-
 
1330
					s += 2;
-
 
1331
				} else {
-
 
1332
					break;
-
 
1333
				}
-
 
1334
			}
-
 
1335
			bfputc(tf,(int)c);
-
 
1336
			s++;
-
 
1337
		}
-
 
1338
		bfputc(tf, 0);
-
 
1339
		h = hash(tf->start);
-
 
1340
		nm = lookup_name(tf->start, h, ext, lex_unknown);
-
 
1341
		id = DEREF_id(hashid_id(nm));
-
 
1342
		break;
-
 
1343
	}
-
 
1344
	case lex_type_Hname:
-
 
1345
	case lex_destructor_Hname: {
-
 
1346
		/* Constructor and destructor names */
-
 
1347
		func = 1;
-
 
1348
		break;
-
 
1349
	}
-
 
1350
	case lex_operator: {
-
 
1351
		/* Conversion function name */
-
 
1352
		TYPE t = unmangle_type(&s, cv_none, btype_none, 1);
-
 
1353
		nm = lookup_conv(t);
-
 
1354
		id = DEREF_id(hashid_id(nm));
-
 
1355
		func = 1;
-
 
1356
		break;
-
 
1357
	}
-
 
1358
	case lex_auto: {
-
 
1359
		/* Anonymous identifier */
-
 
1360
		bfprintf(bf, "<anon>");
-
 
1361
		return (NULL);
-
 
1362
	}
-
 
1363
	case lex_static: {
-
 
1364
		/* Local static variable */
-
 
1365
		bfprintf(bf, "<static>");
-
 
1366
		return (NULL);
-
 
1367
	}
-
 
1368
	case lex_typeof: {
-
 
1369
		/* Run-time type information */
-
 
1370
		TYPE t = unmangle_type(&s, cv_none, btype_none, 1);
-
 
1371
		bfprintf(bf, "typeid ( ");
-
 
1372
		IGNORE print_type(t, bf, 0);
-
 
1373
		bfprintf(bf, " )");
-
 
1374
		return (s);
-
 
1375
	}
-
 
1376
	case lex_virtual: {
-
 
1377
		/* Virtual function table */
-
 
1378
		int sep = 0;
-
 
1379
		bfprintf(bf, "vtable ( ");
-
 
1380
		for (;;) {
-
 
1381
			id = unmangle_nspace(&s, global_namespace, 0);
-
 
1382
			if (IS_NULL_id(id)) {
-
 
1383
				break;
-
 
1384
			}
-
 
1385
			if (sep) {
-
 
1386
				bfprintf(bf, "::");
-
 
1387
			}
-
 
1388
			IGNORE print_id_long(id, qual_none, bf, 0);
-
 
1389
			sep = 1;
-
 
1390
		}
-
 
1391
		if (!sep) {
-
 
1392
			bfprintf(bf, "<error>");
-
 
1393
		}
-
 
1394
		bfprintf(bf, " )");
-
 
1395
		return (s);
-
 
1396
	}
-
 
1397
 
-
 
1398
	default: {
-
 
1399
		/* Operator name */
-
 
1400
		nm = lookup_op(op);
-
 
1401
		if (!IS_NULL_hashid(nm)) {
-
 
1402
			id = DEREF_id(hashid_id(nm));
-
 
1403
			func = 1;
-
 
1404
		}
-
 
1405
		break;
-
 
1406
	}
-
 
1407
	}
-
 
1408
 
-
 
1409
	/* Unmangle identifier namespace and type */
-
 
1410
	if (s[0] == MANGLE_sep && s[1] == MANGLE_sep) {
-
 
1411
		TYPE t;
-
 
1412
		string s0 = s + 2;
-
 
1413
		NAMESPACE pns = global_namespace;
-
 
1414
		IDENTIFIER pid = unmangle_nspace(&s0, pns, 0);
-
 
1415
		character c = *s0;
-
 
1416
		if (c == MANGLE_func_templ) {
-
 
1417
			/* Allow for template functions */
-
 
1418
			s0++;
-
 
1419
			crt_unmangle_args = unmangle_token_args(&s0);
-
 
1420
			if (*s0 == MANGLE_sep) {
-
 
1421
				s0++;
-
 
1422
			}
-
 
1423
		}
-
 
1424
 
1256
	/* Unmangle identifier type */
1425
		/* Unmangle identifier type */
1257
	if ( func ) {
1426
		if (func) {
1258
	    crt_unmangle_class = pid ;
1427
			crt_unmangle_class = pid;
1259
	    t = unmangle_func ( &s0, cv_none, 0 ) ;
1428
			t = unmangle_func(&s0, cv_none, 0);
-
 
1429
		} else {
-
 
1430
			if (c == 0 && !IS_NULL_id(pid)) {
-
 
1431
				t = DEREF_type(id_class_name_etc_defn(pid));
-
 
1432
				pid = NULL_id;
-
 
1433
			} else {
-
 
1434
				crt_unmangle_class = pid;
-
 
1435
				t = unmangle_type(&s0, cv_none, btype_none, 0);
-
 
1436
			}
-
 
1437
		}
-
 
1438
		if (IS_NULL_id(pid)) {
-
 
1439
			member_func_type(NULL_ctype, id_function_tag, t);
-
 
1440
		}
-
 
1441
 
-
 
1442
		/* Look up constructor and destructor names */
-
 
1443
		if (!IS_NULL_id(pid)) {
-
 
1444
			TYPE p = DEREF_type(id_class_name_etc_defn(pid));
-
 
1445
			if (IS_type_compound(p)) {
-
 
1446
				CLASS_TYPE ct =
-
 
1447
				    DEREF_ctype(type_compound_defn(p));
-
 
1448
				pns = DEREF_nspace(ctype_member(ct));
-
 
1449
				if (op == lex_type_Hname) {
-
 
1450
					id = DEREF_id(ctype_constr(ct));
-
 
1451
					nm = DEREF_hashid(id_name(id));
-
 
1452
				} else if (op == lex_destructor_Hname) {
-
 
1453
					id = DEREF_id(ctype_destr(ct));
-
 
1454
					nm = DEREF_hashid(id_name(id));
-
 
1455
				}
-
 
1456
			}
-
 
1457
		}
-
 
1458
		if (IS_NULL_hashid(nm)) {
-
 
1459
			nm = KEYWORD(lex_zzzz);
-
 
1460
		}
-
 
1461
 
-
 
1462
		/* Create result identifier */
-
 
1463
		MAKE_id_function(nm, dspec_extern, pns, crt_loc, t, NULL_id,
-
 
1464
				 id);
-
 
1465
		if (c == MANGLE_func_templ) {
-
 
1466
			/* Set up template function arguments */
-
 
1467
			TYPE form;
-
 
1468
			DECL_SPEC ds = (dspec_extern | dspec_instance);
-
 
1469
			MAKE_type_token(cv_none, id, crt_unmangle_args, form);
-
 
1470
			MAKE_id_function(nm, ds, pns, crt_loc, t, NULL_id, id);
-
 
1471
			COPY_type(id_function_form(id), form);
-
 
1472
		}
-
 
1473
		crt_unmangle_args = NULL_list(TOKEN);
-
 
1474
		crt_unmangle_class = NULL_id;
-
 
1475
		s = s0;
-
 
1476
	}
-
 
1477
 
-
 
1478
	/* Print identifier to buffer */
-
 
1479
	if (IS_NULL_id(id)) {
-
 
1480
		bfprintf(bf, "<error>");
-
 
1481
		s = NULL;
1260
	} else {
1482
	} else {
1261
	    if ( c == 0 && !IS_NULL_id ( pid ) ) {
1483
		print_id_desc++;
1262
		t = DEREF_type ( id_class_name_etc_defn ( pid ) ) ;
1484
		IGNORE print_id_long(id, qual_none, bf, 0);
1263
		pid = NULL_id ;
1485
		print_id_desc--;
1264
	    } else {
-
 
1265
		crt_unmangle_class = pid ;
-
 
1266
		t = unmangle_type ( &s0, cv_none, btype_none, 0 ) ;
-
 
1267
	    }
-
 
1268
	}
1486
	}
1269
	if ( IS_NULL_id ( pid ) ) {
-
 
1270
	    member_func_type ( NULL_ctype, id_function_tag, t ) ;
-
 
1271
	}
-
 
1272
 
-
 
1273
	/* Look up constructor and destructor names */
-
 
1274
	if ( !IS_NULL_id ( pid ) ) {
-
 
1275
	    TYPE p = DEREF_type ( id_class_name_etc_defn ( pid ) ) ;
-
 
1276
	    if ( IS_type_compound ( p ) ) {
-
 
1277
		CLASS_TYPE ct = DEREF_ctype ( type_compound_defn ( p ) ) ;
-
 
1278
		pns = DEREF_nspace ( ctype_member ( ct ) ) ;
-
 
1279
		if ( op == lex_type_Hname ) {
-
 
1280
		    id = DEREF_id ( ctype_constr ( ct ) ) ;
-
 
1281
		    nm = DEREF_hashid ( id_name ( id ) ) ;
-
 
1282
		} else if ( op == lex_destructor_Hname ) {
-
 
1283
		    id = DEREF_id ( ctype_destr ( ct ) ) ;
-
 
1284
		    nm = DEREF_hashid ( id_name ( id ) ) ;
-
 
1285
		}
-
 
1286
	    }
-
 
1287
	}
-
 
1288
	if ( IS_NULL_hashid ( nm ) ) nm = KEYWORD ( lex_zzzz ) ;
-
 
1289
 
-
 
1290
	/* Create result identifier */
-
 
1291
	MAKE_id_function ( nm, dspec_extern, pns, crt_loc, t, NULL_id, id ) ;
-
 
1292
	if ( c == MANGLE_func_templ ) {
-
 
1293
	    /* Set up template function arguments */
-
 
1294
	    TYPE form ;
-
 
1295
	    DECL_SPEC ds = ( dspec_extern | dspec_instance ) ;
-
 
1296
	    MAKE_type_token ( cv_none, id, crt_unmangle_args, form ) ;
-
 
1297
	    MAKE_id_function ( nm, ds, pns, crt_loc, t, NULL_id, id ) ;
-
 
1298
	    COPY_type ( id_function_form ( id ), form ) ;
-
 
1299
	}
-
 
1300
	crt_unmangle_args = NULL_list ( TOKEN ) ;
-
 
1301
	crt_unmangle_class = NULL_id ;
-
 
1302
	s = s0 ;
-
 
1303
    }
-
 
1304
 
-
 
1305
    /* Print identifier to buffer */
-
 
1306
    if ( IS_NULL_id ( id ) ) {
-
 
1307
	bfprintf ( bf, "<error>" ) ;
-
 
1308
	s = NULL ;
-
 
1309
    } else {
-
 
1310
	print_id_desc++ ;
-
 
1311
	IGNORE print_id_long ( id, qual_none, bf, 0 ) ;
-
 
1312
	print_id_desc-- ;
-
 
1313
    }
-
 
1314
    return ( s ) ;
1487
	return (s);
1315
}
1488
}
1316
 
1489
 
1317
 
1490
 
1318
/*
1491
/*
1319
    INITIALISE UNMANGLING ROUTINES
1492
    INITIALISE UNMANGLING ROUTINES
1320
 
1493
 
1321
    This routine initialises the unmangling routines.
1494
    This routine initialises the unmangling routines.
1322
*/
1495
*/
1323
 
1496
 
1324
static void init_unmangle
1497
static void
1325
    PROTO_Z ()
1498
init_unmangle(void)
1326
{
1499
{
1327
    static int done = 0 ;
1500
	static int done = 0;
1328
    if ( !done ) {
1501
	if (!done) {
1329
	MAKE_type_pre ( cv_none, btype_none, qual_none, dummy_ret_type ) ;
1502
		MAKE_type_pre(cv_none, btype_none, qual_none, dummy_ret_type);
1330
	done = 1 ;
1503
		done = 1;
1331
    }
1504
	}
1332
    return ;
1505
	return;
1333
}
1506
}
1334
 
1507
 
1335
 
1508
 
1336
/*
1509
/*
1337
    END OF LANGUAGE DEPENDENT ROUTINES
1510
    END OF LANGUAGE DEPENDENT ROUTINES
1338
 
1511
 
1339
    The remaining routine is the only one included in the C producer.
1512
    The remaining routine is the only one included in the C producer.
1340
*/
1513
*/
1341
 
1514
 
1342
#endif
1515
#endif
1343
 
1516
 
1344
 
1517
 
1345
/*
1518
/*
1346
    UNMANGLE A LIST OF IDENTIFIER NAMES
1519
    UNMANGLE A LIST OF IDENTIFIER NAMES
1347
 
1520
 
1348
    This routine unmangles the list of identifier names p to the file f.
1521
    This routine unmangles the list of identifier names p to the file f.
1349
*/
1522
*/
1350
 
1523
 
1351
void unmangle_list
1524
void
1352
    PROTO_N ( ( p, f, pre ) )
-
 
1353
    PROTO_T ( LIST ( string ) p X FILE *f X int pre )
1525
unmangle_list(LIST(string)p, FILE *f, int pre)
1354
{
1526
{
1355
#if LANGUAGE_CPP
1527
#if LANGUAGE_CPP
1356
    init_unmangle () ;
1528
	init_unmangle();
1357
#endif
1529
#endif
1358
    while ( !IS_NULL_list ( p ) ) {
1530
	while (!IS_NULL_list(p)) {
1359
	string s = DEREF_string ( HEAD_list ( p ) ) ;
1531
		string s = DEREF_string(HEAD_list(p));
1360
	if ( s ) {
1532
		if (s) {
1361
	    BUFFER *bf = clear_buffer ( &mangle_buff, f ) ;
1533
			BUFFER *bf = clear_buffer(&mangle_buff, f);
1362
	    if ( pre ) {
1534
			if (pre) {
1363
		/* Print mapping information */
1535
				/* Print mapping information */
1364
		bfprintf ( bf, "%s -> ", s ) ;
1536
				bfprintf(bf, "%s -> ", s);
1365
	    }
1537
			}
1366
#if LANGUAGE_CPP
1538
#if LANGUAGE_CPP
1367
	    s = unmangle_name ( s, bf ) ;
1539
			s = unmangle_name(s, bf);
-
 
1540
			if (s && *s) {
1368
	    if ( s && *s ) bfprintf ( bf, " ?" ) ;
1541
				bfprintf(bf, " ?");
-
 
1542
			}
1369
#else
1543
#else
1370
	    bfputs ( bf, s ) ;
1544
			bfputs(bf, s);
1371
#endif
1545
#endif
1372
	    bfputc ( bf, '\n' ) ;
1546
			bfputc(bf, '\n');
1373
	    output_buffer ( bf, 1 ) ;
1547
			output_buffer(bf, 1);
-
 
1548
		}
-
 
1549
		p = TAIL_list(p);
1374
	}
1550
	}
1375
	p = TAIL_list ( p ) ;
-
 
1376
    }
-
 
1377
    fflush_v ( f ) ;
1551
	fflush_v(f);
1378
    return ;
1552
	return;
1379
}
1553
}