irmode.c 21.9 KB
Newer Older
Christian Würdig's avatar
Christian Würdig committed
1
/*
2
 * Copyright (C) 1995-2011 University of Karlsruhe.  All right reserved.
Christian Würdig's avatar
Christian Würdig committed
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
 *
 * This file is part of libFirm.
 *
 * This file may be distributed and/or modified under the terms of the
 * GNU General Public License version 2 as published by the Free Software
 * Foundation and appearing in the file LICENSE.GPL included in the
 * packaging of this file.
 *
 * Licensees holding valid libFirm Professional Edition licenses may use
 * this file in accordance with the libFirm Commercial License.
 * Agreement provided with the Software.
 *
 * This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
 * WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
 * PURPOSE.
 */

Matthias Braun's avatar
Matthias Braun committed
20
21
22
23
24
/**
 * @file
 * @brief    Data modes of operations.
 * @author   Martin Trapp, Christian Schaefer, Goetz Lindenmaier, Mathias Heil
 * @version  $Id$
Götz Lindenmaier's avatar
Götz Lindenmaier committed
25
 */
Matthias Braun's avatar
Matthias Braun committed
26
#include "config.h"
Boris Boesler's avatar
added    
Boris Boesler committed
27

Moritz Kroll's avatar
Moritz Kroll committed
28
29
#include <stdlib.h>
#include <string.h>
Michael Beck's avatar
Michael Beck committed
30

Moritz Kroll's avatar
Moritz Kroll committed
31
#include <stddef.h>
32

Moritz Kroll's avatar
Moritz Kroll committed
33
34
35
36
37
38
39
40
41
#include "irprog_t.h"
#include "irmode_t.h"
#include "ident.h"
#include "tv_t.h"
#include "obst.h"
#include "irhooks.h"
#include "irtools.h"
#include "array.h"
#include "error.h"
42
#include "pattern_dmp.h"
Christian Schäfer's avatar
Christian Schäfer committed
43

Michael Beck's avatar
Michael Beck committed
44
/** Obstack to hold all modes. */
45
static struct obstack modes;
Christian Schäfer's avatar
Christian Schäfer committed
46

Michael Beck's avatar
Michael Beck committed
47
/** The list of all currently existing modes. */
Matthias Braun's avatar
Matthias Braun committed
48
49
static ir_mode **mode_list;

50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
const char *get_mode_arithmetic_name(ir_mode_arithmetic ari)
{
#define X(a)    case a: return #a
	switch (ari) {
		X(irma_uninitialized);
		X(irma_none);
		X(irma_twos_complement);
		X(irma_ones_complement);
		X(irma_int_BCD);
		X(irma_ieee754);
		X(irma_float_BCD);
		default: return "<unknown>";
	}
#undef X
}

66
/**
67
 * Compare modes that don't need to have their code field
68
 * correctly set
69
70
71
 *
 * TODO: Add other fields
 **/
72
73
static inline int modes_are_equal(const ir_mode *m, const ir_mode *n)
{
74
75
76
77
78
79
80
81
	if (m == n) return 1;
	if (m->sort         == n->sort &&
		m->arithmetic   == n->arithmetic &&
		m->size         == n->size &&
		m->sign         == n->sign  &&
		m->modulo_shift == n->modulo_shift &&
		m->vector_elem  == n->vector_elem)
		return 1;
Christian Schäfer's avatar
Christian Schäfer committed
82

83
	return 0;
84
}
Matthias Heil's avatar
Matthias Heil committed
85

86
/**
87
 * searches the modes obstack for the given mode and returns
88
 * a pointer on an equal mode already in the array, NULL if
89
90
 * none found
 */
91
92
static ir_mode *find_mode(const ir_mode *m)
{
93
94
	size_t i, n_modes;
	for (i = 0, n_modes = ARR_LEN(mode_list); i < n_modes; ++i) {
Matthias Braun's avatar
Matthias Braun committed
95
		ir_mode *n = mode_list[i];
96
97
98
		if (modes_are_equal(n, m))
			return n;
	}
Michael Beck's avatar
Michael Beck committed
99
100
101
	return NULL;
}

102
103
104
/**
 * sets special values of modes
 */
105
106
static void set_mode_values(ir_mode* mode)
{
107
	switch (get_mode_sort(mode))    {
108
	case irms_reference:
109
110
111
112
113
114
115
	case irms_int_number:
	case irms_float_number:
		mode->min  = get_tarval_min(mode);
		mode->max  = get_tarval_max(mode);
		mode->null = get_tarval_null(mode);
		mode->one  = get_tarval_one(mode);
		mode->minus_one = get_tarval_minus_one(mode);
116
		if (get_mode_sort(mode) != irms_float_number) {
117
118
119
120
			mode->all_one = get_tarval_all_one(mode);
		} else {
			mode->all_one = tarval_bad;
		}
121
122
123
124
125
126
127
128
		break;

	case irms_internal_boolean:
		mode->min  = tarval_b_false;
		mode->max  = tarval_b_true;
		mode->null = tarval_b_false;
		mode->one  = tarval_b_true;
		mode->minus_one = tarval_bad;
129
		mode->all_one = tarval_b_true;
130
131
132
133
134
135
136
137
138
139
140
141
		break;

	case irms_auxiliary:
	case irms_memory:
	case irms_control_flow:
		mode->min  = tarval_bad;
		mode->max  = tarval_bad;
		mode->null = tarval_bad;
		mode->one  = tarval_bad;
		mode->minus_one = tarval_bad;
		break;
	}
142
}
143

144
145
146
/* * *
 * globals defined in irmode.h
 * * */
Matthias Heil's avatar
Matthias Heil committed
147

148
/* --- Predefined modes --- */
Christian Schäfer's avatar
Christian Schäfer committed
149

150
151
152
153
154
/* FIRM internal modes: */
ir_mode *mode_T;
ir_mode *mode_X;
ir_mode *mode_M;
ir_mode *mode_BB;
155
156
ir_mode *mode_ANY;
ir_mode *mode_BAD;
Christian Schäfer's avatar
Christian Schäfer committed
157

158
159
160
161
/* predefined numerical modes: */
ir_mode *mode_F;    /* float */
ir_mode *mode_D;    /* double */
ir_mode *mode_E;    /* long double */
Christian Schäfer's avatar
Christian Schäfer committed
162

163
164
165
166
167
168
169
170
ir_mode *mode_Bs;   /* integral values, signed and unsigned */
ir_mode *mode_Bu;   /* 8 bit */
ir_mode *mode_Hs;   /* 16 bit */
ir_mode *mode_Hu;
ir_mode *mode_Is;   /* 32 bit */
ir_mode *mode_Iu;
ir_mode *mode_Ls;   /* 64 bit */
ir_mode *mode_Lu;
171
172
ir_mode *mode_LLs;  /* 128 bit */
ir_mode *mode_LLu;
Christian Schäfer's avatar
Christian Schäfer committed
173

174
175
ir_mode *mode_b;
ir_mode *mode_P;
Michael Beck's avatar
fixed:    
Michael Beck committed
176
177

/* machine specific modes */
178
179
ir_mode *mode_P_code;   /**< machine specific pointer mode for code addresses */
ir_mode *mode_P_data;   /**< machine specific pointer mode for data addresses */
180

181
182
183
184
185
/* * *
 * functions defined in irmode.h
 * * */

/* JNI access functions */
186
187
188
189
190
191
192
193
194
195
196
197
ir_mode *get_modeT(void) { return mode_T; }
ir_mode *get_modeF(void) { return mode_F; }
ir_mode *get_modeD(void) { return mode_D; }
ir_mode *get_modeE(void) { return mode_E; }
ir_mode *get_modeBs(void) { return mode_Bs; }
ir_mode *get_modeBu(void) { return mode_Bu; }
ir_mode *get_modeHs(void) { return mode_Hs; }
ir_mode *get_modeHu(void) { return mode_Hu; }
ir_mode *get_modeIs(void) { return mode_Is; }
ir_mode *get_modeIu(void) { return mode_Iu; }
ir_mode *get_modeLs(void) { return mode_Ls; }
ir_mode *get_modeLu(void) { return mode_Lu; }
198
199
ir_mode *get_modeLLs(void){ return mode_LLs; }
ir_mode *get_modeLLu(void){ return mode_LLu; }
200
201
202
203
204
205
206
ir_mode *get_modeb(void) { return mode_b; }
ir_mode *get_modeP(void) { return mode_P; }
ir_mode *get_modeX(void) { return mode_X; }
ir_mode *get_modeM(void) { return mode_M; }
ir_mode *get_modeBB(void) { return mode_BB; }
ir_mode *get_modeANY(void) { return mode_ANY; }
ir_mode *get_modeBAD(void) { return mode_BAD; }
207

208

209
210
ir_mode *(get_modeP_code)(void)
{
211
	return _get_modeP_code();
Michael Beck's avatar
Michael Beck committed
212
213
}

214
215
ir_mode *(get_modeP_data)(void)
{
216
	return _get_modeP_data();
217
218
}

219
220
void set_modeP_code(ir_mode *p)
{
221
222
	assert(mode_is_reference(p));
	mode_P_code = p;
223
224
}

225
226
void set_modeP_data(ir_mode *p)
{
227
228
	assert(mode_is_reference(p));
	mode_P_data = p;
229
	mode_P = p;
Michael Beck's avatar
Michael Beck committed
230
}
231

232
/**
233
234
235
 * Registers a new mode.
 *
 * @param new_mode  The new mode template.
236
 */
237
238
static ir_mode *register_mode(const ir_mode *new_mode)
{
239
	ir_mode *mode = NULL;
240

241
	assert(new_mode);
242

243
244
	/* copy mode struct to modes array */
	mode = (ir_mode *)obstack_copy(&modes, new_mode, sizeof(*mode));
Matthias Braun's avatar
Matthias Braun committed
245
	ARR_APP1(ir_mode*, mode_list, mode);
246

247
	mode->kind = k_ir_mode;
248
	mode->type = new_type_primitive(mode);
249

250
251
	/* add the new mode to the irp list of modes */
	add_irp_mode(mode);
252

253
	set_mode_values(mode);
254

255
256
	hook_new_mode(new_mode, mode);
	return mode;
257
258
259
260
261
}

/*
 * Creates a new mode.
 */
262
263
ir_mode *new_ir_mode(const char *name, ir_mode_sort sort, int bit_size, int sign,
                     ir_mode_arithmetic arithmetic, unsigned int modulo_shift)
264
{
265
266
267
268
269
270
271
	ir_mode mode_tmpl;
	ir_mode *mode = NULL;

	mode_tmpl.name         = new_id_from_str(name);
	mode_tmpl.sort         = sort;
	mode_tmpl.size         = bit_size;
	mode_tmpl.sign         = sign ? 1 : 0;
272
273
	mode_tmpl.modulo_shift = (mode_tmpl.sort == irms_int_number ||
	                          mode_tmpl.sort == irms_reference) ? modulo_shift : 0;
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
	mode_tmpl.vector_elem  = 1;
	mode_tmpl.arithmetic   = arithmetic;
	mode_tmpl.link         = NULL;
	mode_tmpl.tv_priv      = NULL;

	mode = find_mode(&mode_tmpl);
	if (mode) {
		hook_new_mode(&mode_tmpl, mode);
		return mode;
	}

	/* sanity checks */
	switch (sort) {
	case irms_auxiliary:
	case irms_control_flow:
	case irms_memory:
	case irms_internal_boolean:
291
		panic("internal modes cannot be user defined");
292
293
294
295
296

	case irms_float_number:
	case irms_int_number:
	case irms_reference:
		mode = register_mode(&mode_tmpl);
297
		break;
298
	}
299
	assert(mode != NULL);
300
	return mode;
301
302
}

303
304
305
/*
 * Creates a new vector mode.
 */
306
307
ir_mode *new_ir_vector_mode(const char *name, ir_mode_sort sort, int bit_size, unsigned num_of_elem, int sign,
                            ir_mode_arithmetic arithmetic, unsigned int modulo_shift)
308
{
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
	ir_mode mode_tmpl;
	ir_mode *mode = NULL;

	mode_tmpl.name         = new_id_from_str(name);
	mode_tmpl.sort         = sort;
	mode_tmpl.size         = bit_size * num_of_elem;
	mode_tmpl.sign         = sign ? 1 : 0;
	mode_tmpl.modulo_shift = (mode_tmpl.sort == irms_int_number) ? modulo_shift : 0;
	mode_tmpl.vector_elem  = num_of_elem;
	mode_tmpl.arithmetic   = arithmetic;
	mode_tmpl.link         = NULL;
	mode_tmpl.tv_priv      = NULL;

	mode = find_mode(&mode_tmpl);
	if (mode) {
		hook_new_mode(&mode_tmpl, mode);
		return mode;
	}

	if (num_of_elem <= 1) {
329
		panic("vector modes should have at least 2 elements");
330
331
332
333
334
335
336
337
	}

	/* sanity checks */
	switch (sort) {
	case irms_auxiliary:
	case irms_control_flow:
	case irms_memory:
	case irms_internal_boolean:
338
		panic("internal modes cannot be user defined");
339
340

	case irms_reference:
341
		panic("only integer and floating point modes can be vectorized");
342
343

	case irms_float_number:
344
		panic("not yet implemented");
345
346
347
348

	case irms_int_number:
		mode = register_mode(&mode_tmpl);
	}
349
	assert(mode != NULL);
350
	return mode;
351
352
}

353
/* Functions for the direct access to all attributes of an ir_mode */
354
355
ident *(get_mode_ident)(const ir_mode *mode)
{
356
	return _get_mode_ident(mode);
Christian Schäfer's avatar
Christian Schäfer committed
357
358
}

359
360
const char *get_mode_name(const ir_mode *mode)
{
361
	return get_id_str(mode->name);
Christian Schäfer's avatar
Christian Schäfer committed
362
363
}

364
365
ir_mode_sort (get_mode_sort)(const ir_mode* mode)
{
366
	return _get_mode_sort(mode);
Götz Lindenmaier's avatar
Götz Lindenmaier committed
367
368
}

369
370
unsigned (get_mode_size_bits)(const ir_mode *mode)
{
371
	return _get_mode_size_bits(mode);
Christian Schäfer's avatar
Christian Schäfer committed
372
373
}

374
375
unsigned (get_mode_size_bytes)(const ir_mode *mode)
{
376
	return _get_mode_size_bytes(mode);
Götz Lindenmaier's avatar
Götz Lindenmaier committed
377
378
}

379
380
int (get_mode_sign)(const ir_mode *mode)
{
381
	return _get_mode_sign(mode);
382
383
}

384
385
ir_mode_arithmetic (get_mode_arithmetic)(const ir_mode *mode)
{
386
	return get_mode_arithmetic(mode);
387
388
}

389
390
391
392
393

/* Attribute modulo shift specifies for modes of kind irms_int_number
 *  whether shift applies modulo to value of bits to shift.  Asserts
 *  if mode is not irms_int_number.
 */
394
395
unsigned int (get_mode_modulo_shift)(const ir_mode *mode)
{
396
	return _get_mode_modulo_shift(mode);
397
398
}

399
400
unsigned int (get_mode_n_vector_elems)(const ir_mode *mode)
{
401
	return _get_mode_vector_elems(mode);
402
403
}

404
405
void *(get_mode_link)(const ir_mode *mode)
{
406
	return _get_mode_link(mode);
407
408
}

409
410
void (set_mode_link)(ir_mode *mode, void *l)
{
411
	_set_mode_link(mode, l);
412
413
}

Matthias Braun's avatar
Matthias Braun committed
414
ir_tarval *get_mode_min(ir_mode *mode)
415
{
416
417
	assert(mode);
	assert(mode_is_data(mode));
Christian Schäfer's avatar
Christian Schäfer committed
418

419
	return mode->min;
Christian Schäfer's avatar
Christian Schäfer committed
420
421
}

Matthias Braun's avatar
Matthias Braun committed
422
ir_tarval *get_mode_max(ir_mode *mode)
423
{
424
425
	assert(mode);
	assert(mode_is_data(mode));
Christian Schäfer's avatar
Christian Schäfer committed
426

427
	return mode->max;
Christian Schäfer's avatar
Christian Schäfer committed
428
429
}

Matthias Braun's avatar
Matthias Braun committed
430
ir_tarval *get_mode_null(ir_mode *mode)
431
{
432
	assert(mode);
433
	assert(mode_is_datab(mode));
Christian Schäfer's avatar
Christian Schäfer committed
434

435
	return mode->null;
Christian Schäfer's avatar
Christian Schäfer committed
436
437
}

Matthias Braun's avatar
Matthias Braun committed
438
ir_tarval *get_mode_one(ir_mode *mode)
439
{
440
	assert(mode);
Matthias Braun's avatar
Matthias Braun committed
441
	assert(mode_is_datab(mode));
Christian Schäfer's avatar
Christian Schäfer committed
442

443
	return mode->one;
Christian Schäfer's avatar
Christian Schäfer committed
444
445
}

Matthias Braun's avatar
Matthias Braun committed
446
ir_tarval *get_mode_minus_one(ir_mode *mode)
447
{
448
449
	assert(mode);
	assert(mode_is_data(mode));
Michael Beck's avatar
Michael Beck committed
450

451
	return mode->minus_one;
Michael Beck's avatar
Michael Beck committed
452
453
}

Matthias Braun's avatar
Matthias Braun committed
454
ir_tarval *get_mode_all_one(ir_mode *mode)
455
{
456
	assert(mode);
Matthias Braun's avatar
Matthias Braun committed
457
	assert(mode_is_datab(mode));
458
459
460
	return mode->all_one;
}

Matthias Braun's avatar
Matthias Braun committed
461
ir_tarval *get_mode_infinite(ir_mode *mode)
462
{
463
464
	assert(mode);
	assert(mode_is_float(mode));
465

466
	return get_tarval_plus_inf(mode);
Christian Schäfer's avatar
Christian Schäfer committed
467
468
}

Matthias Braun's avatar
Matthias Braun committed
469
ir_tarval *get_mode_NAN(ir_mode *mode)
470
{
471
472
	assert(mode);
	assert(mode_is_float(mode));
473

474
	return get_tarval_nan(mode);
Christian Schäfer's avatar
Christian Schäfer committed
475
476
}

477
478
int is_mode(const void *thing)
{
Michael Beck's avatar
Michael Beck committed
479
	return get_kind(thing) == k_ir_mode;
480
481
}

482
483
int (mode_is_signed)(const ir_mode *mode)
{
484
	return _mode_is_signed(mode);
Christian Schäfer's avatar
Christian Schäfer committed
485
486
}

487
488
int (mode_is_float)(const ir_mode *mode)
{
489
	return _mode_is_float(mode);
Christian Schäfer's avatar
Christian Schäfer committed
490
491
}

492
493
int (mode_is_int)(const ir_mode *mode)
{
494
	return _mode_is_int(mode);
Christian Schäfer's avatar
Christian Schäfer committed
495
496
}

497
498
int (mode_is_reference)(const ir_mode *mode)
{
499
	return _mode_is_reference(mode);
500
501
}

502
503
int (mode_is_num)(const ir_mode *mode)
{
504
	return _mode_is_num(mode);
Christian Schäfer's avatar
Christian Schäfer committed
505
506
}

507
508
int (mode_is_data)(const ir_mode *mode)
{
509
	return _mode_is_data(mode);
Christian Schäfer's avatar
Christian Schäfer committed
510
511
}

512
513
int (mode_is_datab)(const ir_mode *mode)
{
514
	return _mode_is_datab(mode);
Christian Schäfer's avatar
Christian Schäfer committed
515
516
}

517
518
int (mode_is_dataM)(const ir_mode *mode)
{
519
	return _mode_is_dataM(mode);
Christian Schäfer's avatar
Christian Schäfer committed
520
}
521

522
523
int (mode_is_float_vector)(const ir_mode *mode)
{
524
	return _mode_is_float_vector(mode);
525
526
}

527
528
int (mode_is_int_vector)(const ir_mode *mode)
{
529
	return _mode_is_int_vector(mode);
Michael Beck's avatar
Michael Beck committed
530
531
}

532
/* Returns true if sm can be converted to lm without loss. */
533
534
int smaller_mode(const ir_mode *sm, const ir_mode *lm)
{
535
	int sm_bits, lm_bits;
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589

	assert(sm);
	assert(lm);

	if (sm == lm) return 1;

	sm_bits = get_mode_size_bits(sm);
	lm_bits = get_mode_size_bits(lm);

	switch (get_mode_sort(sm)) {
	case irms_int_number:
		switch (get_mode_sort(lm)) {
		case irms_int_number:
			if (get_mode_arithmetic(sm) != get_mode_arithmetic(lm))
				return 0;

			/* only two complement implemented */
			assert(get_mode_arithmetic(sm) == irma_twos_complement);

			/* integers are convertable if
			 *   - both have the same sign and lm is the larger one
			 *   - lm is the signed one and is at least two bits larger
			 *     (one for the sign, one for the highest bit of sm)
			 *   - sm & lm are two_complement and lm has greater or equal number of bits
			 */
			if (mode_is_signed(sm)) {
				if (!mode_is_signed(lm))
					return 0;
				return sm_bits <= lm_bits;
			} else {
				if (mode_is_signed(lm)) {
					return sm_bits < lm_bits;
				}
				return sm_bits <= lm_bits;
			}

		case irms_float_number:
			/* int to float works if the float is large enough */
			return 0;

		default:
			break;
		}
		break;

	case irms_float_number:
		if (get_mode_arithmetic(sm) == get_mode_arithmetic(lm)) {
			if ( (get_mode_sort(lm) == irms_float_number)
				&& (get_mode_size_bits(lm) >= get_mode_size_bits(sm)) )
				return 1;
		}
		break;

	case irms_reference:
Michael Beck's avatar
Michael Beck committed
590
		/* do exist machines out there with different pointer lengths ?*/
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
		return 0;

	case irms_internal_boolean:
		return mode_is_int(lm);

	default:
		break;
	}

	/* else */
	return 0;
}

/* Returns true if a value of mode sm can be converted into mode lm
   and backwards without loss. */
606
607
int values_in_mode(const ir_mode *sm, const ir_mode *lm)
{
Moritz Kroll's avatar
Moritz Kroll committed
608
	ir_mode_arithmetic arith;
609
610
611
612
613
614

	assert(sm);
	assert(lm);

	if (sm == lm) return 1;

Moritz Kroll's avatar
Moritz Kroll committed
615
616
617
618
619
	if (sm == mode_b)
		return mode_is_int(lm);

	arith = get_mode_arithmetic(sm);
	if (arith != get_mode_arithmetic(lm))
620
621
		return 0;

Moritz Kroll's avatar
Moritz Kroll committed
622
623
624
625
	switch (arith) {
		case irma_twos_complement:
		case irma_ieee754:
			return get_mode_size_bits(sm) <= get_mode_size_bits(lm);
626

Moritz Kroll's avatar
Moritz Kroll committed
627
628
		default:
			return 0;
629
630
631
632
	}
}

/* Return the signed integer equivalent mode for an reference mode. */
633
634
ir_mode *get_reference_mode_signed_eq(ir_mode *mode)
{
635
636
637
638
639
	assert(mode_is_reference(mode));
	return mode->eq_signed;
}

/* Sets the signed integer equivalent mode for an reference mode. */
640
641
void set_reference_mode_signed_eq(ir_mode *ref_mode, ir_mode *int_mode)
{
642
643
644
645
646
647
	assert(mode_is_reference(ref_mode));
	assert(mode_is_int(int_mode));
	ref_mode->eq_signed = int_mode;
}

/* Return the unsigned integer equivalent mode for an reference mode. */
648
649
ir_mode *get_reference_mode_unsigned_eq(ir_mode *mode)
{
650
651
652
653
654
	assert(mode_is_reference(mode));
	return mode->eq_unsigned;
}

/* Sets the unsigned integer equivalent mode for an reference mode. */
655
656
void set_reference_mode_unsigned_eq(ir_mode *ref_mode, ir_mode *int_mode)
{
657
658
659
	assert(mode_is_reference(ref_mode));
	assert(mode_is_int(int_mode));
	ref_mode->eq_unsigned = int_mode;
660
661
}

662
/* initialization, build the default modes */
663
664
void init_mode(void)
{
665
	ir_mode newmode;
666

667
	obstack_init(&modes);
Matthias Braun's avatar
Matthias Braun committed
668
	mode_list = NEW_ARR_F(ir_mode*, 0);
669

670
	/* initialize predefined modes */
671

672
673
674
675
676
677
678
679
680
681
	/* Internal Modes */
	newmode.arithmetic   = irma_none;
	newmode.size         = 0;
	newmode.sign         = 0;
	newmode.modulo_shift = 0;
	newmode.vector_elem  = 0;
	newmode.eq_signed    = NULL;
	newmode.eq_unsigned  = NULL;
	newmode.link         = NULL;
	newmode.tv_priv      = NULL;
682

683
684
	/* Control Flow Modes*/
	newmode.sort    = irms_control_flow;
685

686
687
	/* Basic Block */
	newmode.name    = new_id_from_chars("BB", 2);
688
	mode_BB         = register_mode(&newmode);
689

690
691
	/* eXecution */
	newmode.name    = new_id_from_chars("X", 1);
692
	mode_X          = register_mode(&newmode);
693

694
695
	/* Memory Modes */
	newmode.sort    = irms_memory;
696

697
698
	/* Memory */
	newmode.name    = new_id_from_chars("M", 1);
699
	mode_M          = register_mode(&newmode);
700

701
702
	/* Auxiliary Modes */
	newmode.sort    = irms_auxiliary,
703

704
705
	/* Tuple */
	newmode.name    = new_id_from_chars("T", 1);
706
	mode_T          = register_mode(&newmode);
707

708
709
	/* ANY */
	newmode.name    = new_id_from_chars("ANY", 3);
710
	mode_ANY        = register_mode(&newmode);
711

712
713
	/* BAD */
	newmode.name    = new_id_from_chars("BAD", 3);
714
	mode_BAD        = register_mode(&newmode);
715

716
717
	/* Internal Boolean Modes */
	newmode.sort    = irms_internal_boolean;
718

719
720
	/* boolean */
	newmode.name    = new_id_from_chars("b", 1);
721
	mode_b          = register_mode(&newmode);
722

723
724
	/* Data Modes */
	newmode.vector_elem = 1;
725

726
727
728
	/* Float Number Modes */
	newmode.sort       = irms_float_number;
	newmode.arithmetic = irma_ieee754;
729

730
731
732
733
	/* float */
	newmode.name    = new_id_from_chars("F", 1);
	newmode.sign    = 1;
	newmode.size    = 32;
734
	mode_F          = register_mode(&newmode);
735

736
737
738
739
	/* double */
	newmode.name    = new_id_from_chars("D", 1);
	newmode.sign    = 1;
	newmode.size    = 64;
740
	mode_D          = register_mode(&newmode);
741

742
743
744
	/* extended */
	newmode.name    = new_id_from_chars("E", 1);
	newmode.sign    = 1;
Matthias Braun's avatar
Matthias Braun committed
745
746
747
	/* note that the tarval module is calculating with 80 bits, but we use
	 * 96 bits, as that is what will be stored to memory by most hardware */
	newmode.size    = 96;
748
	mode_E          = register_mode(&newmode);
749

750
751
752
	/* Integer Number Modes */
	newmode.sort         = irms_int_number;
	newmode.arithmetic   = irma_twos_complement;
753

754
755
756
757
758
	/* signed byte */
	newmode.name         = new_id_from_chars("Bs", 2);
	newmode.sign         = 1;
	newmode.size         = 8;
	newmode.modulo_shift = 32;
759
	mode_Bs              = register_mode(&newmode);
760

761
762
763
764
765
766
	/* unsigned byte */
	newmode.name         = new_id_from_chars("Bu", 2);
	newmode.arithmetic   = irma_twos_complement;
	newmode.sign         = 0;
	newmode.size         = 8;
	newmode.modulo_shift = 32;
767
	mode_Bu              = register_mode(&newmode);
768

769
770
771
772
773
	/* signed short integer */
	newmode.name         = new_id_from_chars("Hs", 2);
	newmode.sign         = 1;
	newmode.size         = 16;
	newmode.modulo_shift = 32;
774
	mode_Hs              = register_mode(&newmode);
775

776
777
778
779
780
	/* unsigned short integer */
	newmode.name         = new_id_from_chars("Hu", 2);
	newmode.sign         = 0;
	newmode.size         = 16;
	newmode.modulo_shift = 32;
781
	mode_Hu              = register_mode(&newmode);
782

783
784
785
786
787
	/* signed integer */
	newmode.name         = new_id_from_chars("Is", 2);
	newmode.sign         = 1;
	newmode.size         = 32;
	newmode.modulo_shift = 32;
788
	mode_Is              = register_mode(&newmode);
789

790
791
792
793
794
	/* unsigned integer */
	newmode.name         = new_id_from_chars("Iu", 2);
	newmode.sign         = 0;
	newmode.size         = 32;
	newmode.modulo_shift = 32;
795
	mode_Iu              = register_mode(&newmode);
796
797
798
799
800
801

	/* signed long integer */
	newmode.name         = new_id_from_chars("Ls", 2);
	newmode.sign         = 1;
	newmode.size         = 64;
	newmode.modulo_shift = 64;
802
	mode_Ls              = register_mode(&newmode);
803
804
805
806
807
808

	/* unsigned long integer */
	newmode.name         = new_id_from_chars("Lu", 2);
	newmode.sign         = 0;
	newmode.size         = 64;
	newmode.modulo_shift = 64;
809
	mode_Lu              = register_mode(&newmode);
810

811
812
813
814
815
	/* signed long long integer */
	newmode.name         = new_id_from_chars("LLs", 3);
	newmode.sign         = 1;
	newmode.size         = 128;
	newmode.modulo_shift = 128;
816
	mode_LLs             = register_mode(&newmode);
817
818
819
820
821
822

	/* unsigned long long integer */
	newmode.name         = new_id_from_chars("LLu", 3);
	newmode.sign         = 0;
	newmode.size         = 128;
	newmode.modulo_shift = 128;
823
	mode_LLu             = register_mode(&newmode);
824

825
826
	/* Reference Mode */
	newmode.sort       = irms_reference;
827
828
829
830
831
832
	newmode.arithmetic = irma_twos_complement;

	/* pointer */
	newmode.name         = new_id_from_chars("P", 1);
	newmode.sign         = 0;
	newmode.size         = 32;
833
	newmode.modulo_shift = 32;
834
835
	newmode.eq_signed    = mode_Is;
	newmode.eq_unsigned  = mode_Iu;
836
	mode_P               = register_mode(&newmode);
837
838
839
840

	/* set the machine specific modes to the predefined ones */
	mode_P_code = mode_P;
	mode_P_data = mode_P;
841
}
842

Michael Beck's avatar
Michael Beck committed
843
/* find a signed mode for an unsigned integer mode */
844
845
ir_mode *find_unsigned_mode(const ir_mode *mode)
{
846
	ir_mode n = *mode;
847

848
849
850
851
852
	/* allowed for reference mode */
	if (mode->sort == irms_reference)
		n.sort = irms_int_number;

	assert(n.sort == irms_int_number);
853
854
	n.sign = 0;
	return find_mode(&n);
855
856
}

Michael Beck's avatar
Michael Beck committed
857
/* find an unsigned mode for a signed integer mode */
858
859
ir_mode *find_signed_mode(const ir_mode *mode)
{
860
	ir_mode n = *mode;
861

862
863
864
	assert(mode->sort == irms_int_number);
	n.sign = 1;
	return find_mode(&n);
865
866
}

Michael Beck's avatar
Michael Beck committed
867
/* finds a integer mode with 2*n bits for an integer mode with n bits. */
868
869
ir_mode *find_double_bits_int_mode(const ir_mode *mode)
{
870
	ir_mode n = *mode;
Michael Beck's avatar
Michael Beck committed
871

872
	assert(mode->sort == irms_int_number && mode->arithmetic == irma_twos_complement);
Michael Beck's avatar
Michael Beck committed
873

874
875
	n.size = 2*mode->size;
	return find_mode(&n);
Michael Beck's avatar
Michael Beck committed
876
}
877

878
879
880
881
/*
 * Returns non-zero if the given mode honors signed zero's, i.e.,
 * a +0 and a -0 exists and handled differently.
 */
882
883
int mode_honor_signed_zeros(const ir_mode *mode)
{
884
885
886
	/* for floating point, we know that IEEE 754 has +0 and -0,
	 * but always handles it identical.
	 */
Christian Würdig's avatar
Christian Würdig committed
887
888
889
	return
		mode->sort == irms_float_number &&
		mode->arithmetic != irma_ieee754;
890
891
}

892
893
894
895
896
/*
 * Returns non-zero if the given mode might overflow on unary Minus.
 *
 * This does NOT happen on IEEE 754.
 */
897
898
int mode_overflow_on_unary_Minus(const ir_mode *mode)
{
899
900
901
	if (mode->sort == irms_float_number)
		return mode->arithmetic == irma_ieee754 ? 0 : 1;
	return 1;
902
903
}

Michael Beck's avatar
Michael Beck committed
904
/*
905
 * Returns non-zero if the mode has a reversed wrap-around
Michael Beck's avatar
Michael Beck committed
906
907
908
909
910
 * logic, especially (a + x) - x == a.
 *
 * This is normally true for integer modes, not for floating
 * point modes.
 */
911
912
int mode_wrap_around(const ir_mode *mode)
{
913
914
	/* FIXME: better would be an extra mode property */
	return mode_is_int(mode);
Michael Beck's avatar
Michael Beck committed
915
916
}

917
918
919
920
921
/*
 * Returns non-zero if the cast from mode src to mode dst is a
 * reinterpret cast (ie. only the bit pattern is reinterpreted,
 * no conversion is done)
 */
922
923
int is_reinterpret_cast(const ir_mode *src, const ir_mode *dst)
{
924
925
926
927
928
929
930
931
932
933
934
935
936
	ir_mode_arithmetic ma;

	if (src == dst)
		return 1;
	if (get_mode_size_bits(src) != get_mode_size_bits(dst))
		return 0;
	ma = get_mode_arithmetic(src);
	if (ma != get_mode_arithmetic(dst))
		return 0;

	return ma == irma_twos_complement || ma == irma_ones_complement;
}

937
938
939
940
941
ir_type *(get_type_for_mode) (const ir_mode *mode)
{
	return get_type_for_mode_(mode);
}

942
943
void finish_mode(void)
{
944
	obstack_free(&modes, 0);
Matthias Braun's avatar
Matthias Braun committed
945
	DEL_ARR_F(mode_list);
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968

	mode_T   = NULL;
	mode_X   = NULL;
	mode_M   = NULL;
	mode_BB  = NULL;
	mode_ANY = NULL;
	mode_BAD = NULL;

	mode_F   = NULL;
	mode_D   = NULL;
	mode_E   = NULL;

	mode_Bs  = NULL;
	mode_Bu  = NULL;
	mode_Hs  = NULL;
	mode_Hu  = NULL;
	mode_Is  = NULL;
	mode_Iu  = NULL;
	mode_Ls  = NULL;
	mode_Lu  = NULL;

	mode_b   = NULL;

969
	mode_P      = NULL;
970
971
	mode_P_code = NULL;
	mode_P_data = NULL;
972
}