2e82675055b01a91df00b07341e31cd90c9e8efa
[libfirm] / ir / tv / tv.c
1 /*
2  * Copyright (C) 1995-2007 University of Karlsruhe.  All right reserved.
3  *
4  * This file is part of libFirm.
5  *
6  * This file may be distributed and/or modified under the terms of the
7  * GNU General Public License version 2 as published by the Free Software
8  * Foundation and appearing in the file LICENSE.GPL included in the
9  * packaging of this file.
10  *
11  * Licensees holding valid libFirm Professional Edition licenses may use
12  * this file in accordance with the libFirm Commercial License.
13  * Agreement provided with the Software.
14  *
15  * This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
16  * WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
17  * PURPOSE.
18  */
19
20 /**
21  * @file
22  * @brief    Representation of and static computations on target machine
23  *           values.
24  * @date     2003
25  * @author   Mathias Heil
26  * @version  $Id$
27  * @summary
28  *
29  * Values are stored in a format depending upon chosen arithmetic
30  * module. Default uses strcalc and fltcalc.
31  * This implementation assumes:
32  *  - target has IEEE-754 floating-point arithmetic.
33  */
34 #ifdef HAVE_CONFIG_H
35 # include "config.h"
36 #endif
37
38 #include <assert.h>         /* assertions */
39 #include <stdlib.h>         /* atoi() */
40 #ifdef HAVE_STRING_H
41 # include <string.h>         /* nice things for strings */
42 #endif
43 #ifdef HAVE_STRINGS_H
44 #include <strings.h>        /* strings.h also includes bsd only function strcasecmp */
45 #endif
46 #ifdef HAVE_STDLIB_H
47 # include <stdlib.h>
48 #endif
49
50 #include "tv_t.h"
51 #include "set.h"            /* to store tarvals in */
52 #include "entity_t.h"       /* needed to store pointers to entities */
53 #include "irmode_t.h"
54 #include "irnode.h"         /* defines boolean return values (pnc_number)*/
55 #include "strcalc.h"
56 #include "fltcalc.h"
57 #include "irtools.h"
58 #include "xmalloc.h"
59 #include "firm_common.h"
60 #include "error.h"
61
62 /** Size of hash tables.  Should correspond to average number of distinct constant
63     target values */
64 #define N_CONSTANTS 2048
65
66 /* get the integer overflow mode */
67 #define GET_OVERFLOW_MODE() int_overflow_mode
68
69 /* unused, float to int doesn't work yet */
70 enum float_to_int_mode {
71         TRUNCATE,
72         ROUND
73 };
74
75 #define GET_FLOAT_TO_INT_MODE() TRUNCATE
76
77 #define SWITCH_NOINFINITY 0
78 #define SWITCH_NODENORMALS 0
79
80 /****************************************************************************
81  *   local definitions and macros
82  ****************************************************************************/
83 #ifndef NDEBUG
84 #  define TARVAL_VERIFY(a) tarval_verify((a))
85 #else
86 #  define TARVAL_VERIFY(a) ((void)0)
87 #endif
88
89 #define INSERT_TARVAL(tv) ((tarval*)set_insert(tarvals, (tv), sizeof(tarval), hash_tv((tv))))
90 #define FIND_TARVAL(tv) ((tarval*)set_find(tarvals, (tv), sizeof(tarval), hash_tv((tv))))
91
92 #define INSERT_VALUE(val, size) (set_insert(values, (val), size, hash_val((val), size)))
93 #define FIND_VALUE(val, size) (set_find(values, (val), size, hash_val((val), size)))
94
95 #define fail_verify(a) _fail_verify((a), __FILE__, __LINE__)
96
97 /****************************************************************************
98  *   private variables
99  ****************************************************************************/
100 static struct set *tarvals = NULL;   /* container for tarval structs */
101 static struct set *values = NULL;    /* container for values */
102 static tarval_int_overflow_mode_t int_overflow_mode = TV_OVERFLOW_WRAP;
103
104 /** if this is set non-zero, the constant folding for floating point is OFF */
105 static int no_float = 0;
106
107 /****************************************************************************
108  *   private functions
109  ****************************************************************************/
110 #ifndef NDEBUG
111 static int hash_val(const void *value, unsigned int length);
112 static int hash_tv(tarval *tv);
113 static void _fail_verify(tarval *tv, const char* file, int line)
114 {
115         /* print a memory image of the tarval and throw an assertion */
116         if (tv)
117                 printf("%s:%d: Invalid tarval:\n  mode: %s\n value: [%p]\n", file, line, get_mode_name(tv->mode), tv->value);
118         else
119                 printf("%s:%d: Invalid tarval (null)", file, line);
120         assert(0);
121 }
122 #ifdef __GNUC__
123 INLINE static void tarval_verify(tarval *tv) __attribute__ ((unused));
124 #endif
125
126 INLINE static void tarval_verify(tarval *tv)
127 {
128         assert(tv);
129         assert(tv->mode);
130         assert(tv->value);
131
132         if ((tv == tarval_bad) || (tv == tarval_undefined)) return;
133         if ((tv == tarval_b_true) || (tv == tarval_b_false)) return;
134
135         if (!FIND_TARVAL(tv)) fail_verify(tv);
136         if (tv->length > 0 && !FIND_VALUE(tv->value, tv->length)) fail_verify(tv);
137
138         return;
139 }
140 #endif /* NDEBUG */
141
142 /** Hash a tarval. */
143 static int hash_tv(tarval *tv) {
144         return (PTR_TO_INT(tv->value) ^ PTR_TO_INT(tv->mode)) + tv->length;
145 }
146
147 /** Hash a value. Treat it as a byte array. */
148 static int hash_val(const void *value, unsigned int length) {
149         unsigned int i;
150         unsigned int hash = 0;
151
152         /* scramble the byte - array */
153         for (i = 0; i < length; ++i) {
154                 hash += (hash << 5) ^ (hash >> 27) ^ ((char*)value)[i];
155                 hash += (hash << 11) ^ (hash >> 17);
156         }
157
158         return hash;
159 }
160
161 /** finds tarval with value/mode or creates new tarval */
162 static tarval *get_tarval(const void *value, int length, ir_mode *mode) {
163         tarval tv;
164
165         tv.kind   = k_tarval;
166         tv.mode   = mode;
167         tv.length = length;
168         if (length > 0) {
169                 /* if there already is such a value, it is returned, else value
170                  * is copied into the set */
171                 char *temp = alloca(sc_get_buffer_length());
172                 memcpy(temp, value, sc_get_buffer_length());
173                 sign_extend(temp, mode);
174                 tv.value = INSERT_VALUE(temp, length);
175         } else {
176                 tv.value = value;
177         }
178         /* if there is such a tarval, it is returned, else tv is copied
179          * into the set */
180         return (tarval *)INSERT_TARVAL(&tv);
181 }
182
183 /**
184  * handle overflow
185  */
186 static tarval *get_tarval_overflow(const void *value, int length, ir_mode *mode)
187 {
188         char *temp;
189
190         switch (get_mode_sort(mode)) {
191         case irms_reference:
192                 /* addresses always wrap around */
193                 temp = alloca(sc_get_buffer_length());
194                 sc_val_from_ulong(-1, temp);
195                 sc_and(temp, value, temp);
196                 /* the sc_ module expects that all bits are set ... */
197                 sign_extend(temp, mode);
198                 return get_tarval(temp, length, mode);
199
200         case irms_int_number:
201                 if (sc_comp(value, get_mode_max(mode)->value) == 1) {
202                         switch (GET_OVERFLOW_MODE()) {
203                         case TV_OVERFLOW_SATURATE:
204                                 return get_mode_max(mode);
205                         case TV_OVERFLOW_WRAP:
206                                 temp = alloca(sc_get_buffer_length());
207                                 sc_val_from_ulong(-1, temp);
208                                 sc_and(temp, value, temp);
209                                 /* the sc_ module expects that all bits are set ... */
210                                 sign_extend(temp, mode);
211                                 return get_tarval(temp, length, mode);
212                         case TV_OVERFLOW_BAD:
213                                 return tarval_bad;
214                         default:
215                                 return get_tarval(value, length, mode);
216                         }
217                 }
218                 if (sc_comp(value, get_mode_min(mode)->value) == -1) {
219                         switch (GET_OVERFLOW_MODE()) {
220                         case TV_OVERFLOW_SATURATE:
221                                 return get_mode_min(mode);
222                         case TV_OVERFLOW_WRAP: {
223                                 char *temp = alloca(sc_get_buffer_length());
224                                 sc_val_from_ulong(-1, temp);
225                                 sc_and(temp, value, temp);
226                                 return get_tarval(temp, length, mode);
227                         }
228                         case TV_OVERFLOW_BAD:
229                                 return tarval_bad;
230                         default:
231                                 return get_tarval(value, length, mode);
232                         }
233                 }
234                 break;
235
236         case irms_float_number:
237                 if (SWITCH_NOINFINITY && fc_is_inf(value)) {
238                         return fc_is_negative(value)?get_mode_min(mode):get_mode_max(mode);
239                 }
240
241                 if (SWITCH_NODENORMALS && fc_is_subnormal(value)) {
242                         return get_mode_null(mode);
243                 }
244                 break;
245
246         default:
247                 break;
248         }
249         return get_tarval(value, length, mode);
250 }
251
252 /*
253  *   public variables declared in tv.h
254  */
255 static tarval reserved_tv[4];
256
257 tarval *tarval_bad       = &reserved_tv[0];
258 tarval *tarval_undefined = &reserved_tv[1];
259 tarval *tarval_b_false   = &reserved_tv[2];
260 tarval *tarval_b_true    = &reserved_tv[3];
261
262 /*
263  *   public functions declared in tv.h
264  */
265
266 /*
267  * Constructors =============================================================
268  */
269 tarval *new_tarval_from_str(const char *str, size_t len, ir_mode *mode)
270 {
271         assert(str);
272         assert(len);
273         assert(mode);
274
275         switch (get_mode_sort(mode)) {
276         case irms_control_flow:
277         case irms_memory:
278         case irms_auxiliary:
279                 assert(0);
280                 break;
281
282         case irms_internal_boolean:
283                 /* match [tT][rR][uU][eE]|[fF][aA][lL][sS][eE] */
284                 if (strcasecmp(str, "true")) return tarval_b_true;
285                 else if (strcasecmp(str, "false")) return tarval_b_true;
286                 else
287                         /* XXX This is C semantics */
288                         return atoi(str) ? tarval_b_true : tarval_b_false;
289
290         case irms_float_number:
291                 switch (get_mode_size_bits(mode)) {
292                 case 32:
293                         fc_val_from_str(str, len, 8, 23, NULL);
294                         break;
295                 case 64:
296                         fc_val_from_str(str, len, 11, 52, NULL);
297                         break;
298                 case 80:
299                         fc_val_from_str(str, len, 15, 64, NULL);
300                         break;
301                 }
302                 return get_tarval(fc_get_buffer(), fc_get_buffer_length(), mode);
303
304         case irms_reference:
305                 /* same as integer modes */
306         case irms_int_number:
307                 sc_val_from_str(str, len, NULL, mode);
308                 return get_tarval(sc_get_buffer(), sc_get_buffer_length(), mode);
309         }
310
311         assert(0);  /* can't be reached, can it? */
312         return NULL;
313 }
314
315 /*
316  * helper function, create a tarval from long
317  */
318 tarval *new_tarval_from_long(long l, ir_mode *mode) {
319         assert(mode);
320
321         switch (get_mode_sort(mode))   {
322         case irms_internal_boolean:
323                 /* XXX C semantics ! */
324                 return l ? tarval_b_true : tarval_b_false ;
325
326         case irms_reference:
327                 /* same as integer modes */
328         case irms_int_number:
329                 sc_val_from_long(l, NULL);
330                 return get_tarval(sc_get_buffer(), sc_get_buffer_length(), mode);
331
332         case irms_float_number:
333                 return new_tarval_from_double((long double)l, mode);
334
335         default:
336                 assert(0 && "unsupported mode sort");
337         }
338         return NULL;
339 }
340
341 /* returns non-zero if can be converted to long */
342 int tarval_is_long(tarval *tv) {
343         if (!mode_is_int(tv->mode) && !mode_is_reference(tv->mode))
344                 return 0;
345
346         if (get_mode_size_bits(tv->mode) > (int) (sizeof(long) << 3)) {
347                 /* the value might be too big to fit in a long */
348                 sc_max_from_bits(sizeof(long) << 3, 0, NULL);
349                 if (sc_comp(sc_get_buffer(), tv->value) == -1) {
350                         /* really doesn't fit */
351                         return 0;
352                 }
353         }
354         return 1;
355 }
356
357 /* this might overflow the machine's long, so use only with small values */
358 long get_tarval_long(tarval* tv) {
359         assert(tarval_is_long(tv) && "tarval too big to fit in long");
360
361         return sc_val_to_long(tv->value);
362 }
363
364 tarval *new_tarval_from_double(long double d, ir_mode *mode) {
365         assert(mode && (get_mode_sort(mode) == irms_float_number));
366
367         switch (get_mode_size_bits(mode)) {
368         case 32:
369                 fc_val_from_ieee754(d, 8, 23, NULL);
370                 break;
371         case 64:
372                 fc_val_from_ieee754(d, 11, 52, NULL);
373                 break;
374         case 80:
375                 fc_val_from_ieee754(d, 15, 64, NULL);
376                 break;
377         }
378         return get_tarval(fc_get_buffer(), fc_get_buffer_length(), mode);
379 }
380
381 /* returns non-zero if can be converted to double */
382 int tarval_is_double(tarval *tv) {
383         assert(tv);
384
385         return (get_mode_sort(tv->mode) == irms_float_number);
386 }
387
388 long double get_tarval_double(tarval *tv) {
389         assert(tarval_is_double(tv));
390
391         return fc_val_to_ieee754(tv->value);
392 }
393
394
395 /*
396  * Access routines for tarval fields ========================================
397  */
398
399 /* get the mode of the tarval */
400 ir_mode *(get_tarval_mode)(const tarval *tv) {
401         return _get_tarval_mode(tv);
402 }
403
404 /*
405  * Special value query functions ============================================
406  *
407  * These functions calculate and return a tarval representing the requested
408  * value.
409  * The functions get_mode_{Max,Min,...} return tarvals retrieved from these
410  * functions, but these are stored on initialization of the irmode module and
411  * therefore the irmode functions should be preferred to the functions below.
412  */
413
414 tarval *(get_tarval_bad)(void) {
415         return _get_tarval_bad();
416 }
417
418 tarval *(get_tarval_undefined)(void) {
419         return _get_tarval_undefined();
420 }
421
422 tarval *(get_tarval_b_false)(void) {
423         return _get_tarval_b_false();
424 }
425
426 tarval *(get_tarval_b_true)(void) {
427         return _get_tarval_b_true();
428 }
429
430 tarval *get_tarval_max(ir_mode *mode) {
431         assert(mode);
432
433         if (get_mode_n_vector_elems(mode) > 1) {
434                 /* vector arithmetic not implemented yet */
435                 return tarval_bad;
436         }
437
438         switch(get_mode_sort(mode)) {
439         case irms_control_flow:
440         case irms_memory:
441         case irms_auxiliary:
442                 assert(0);
443                 break;
444
445         case irms_internal_boolean:
446                 return tarval_b_true;
447
448         case irms_float_number:
449                 switch(get_mode_size_bits(mode)) {
450                 case 32:
451                         fc_get_max(8, 23, NULL);
452                         break;
453                 case 64:
454                         fc_get_max(11, 52, NULL);
455                         break;
456                 case 80:
457                         fc_get_max(15, 64, NULL);
458                         break;
459                 }
460                 return get_tarval(fc_get_buffer(), fc_get_buffer_length(), mode);
461
462         case irms_reference:
463         case irms_int_number:
464                 sc_max_from_bits(get_mode_size_bits(mode), mode_is_signed(mode), NULL);
465                 return get_tarval(sc_get_buffer(), sc_get_buffer_length(), mode);
466         }
467         return tarval_bad;
468 }
469
470 tarval *get_tarval_min(ir_mode *mode) {
471         assert(mode);
472
473         if (get_mode_n_vector_elems(mode) > 1) {
474                 /* vector arithmetic not implemented yet */
475                 return tarval_bad;
476         }
477
478         switch(get_mode_sort(mode)) {
479         case irms_control_flow:
480         case irms_memory:
481         case irms_auxiliary:
482                 assert(0);
483                 break;
484
485         case irms_internal_boolean:
486                 return tarval_b_false;
487
488         case irms_float_number:
489                 switch(get_mode_size_bits(mode)) {
490                 case 32:
491                         fc_get_min(8, 23, NULL);
492                         break;
493                 case 64:
494                         fc_get_min(11, 52, NULL);
495                         break;
496                 case 80:
497                         fc_get_min(15, 64, NULL);
498                         break;
499                 }
500                 return get_tarval(fc_get_buffer(), fc_get_buffer_length(), mode);
501
502         case irms_reference:
503         case irms_int_number:
504                 sc_min_from_bits(get_mode_size_bits(mode), mode_is_signed(mode), NULL);
505                 return get_tarval(sc_get_buffer(), sc_get_buffer_length(), mode);
506         }
507         return tarval_bad;
508 }
509
510 /** The bit pattern for the pointer NULL */
511 static long _null_value = 0;
512
513 tarval *get_tarval_null(ir_mode *mode) {
514         assert(mode);
515
516         if (get_mode_n_vector_elems(mode) > 1) {
517                 /* vector arithmetic not implemented yet */
518                 return tarval_bad;
519         }
520
521         switch(get_mode_sort(mode)) {
522         case irms_control_flow:
523         case irms_memory:
524         case irms_auxiliary:
525         case irms_internal_boolean:
526                 assert(0);
527                 break;
528
529         case irms_float_number:
530                 return new_tarval_from_double(0.0, mode);
531
532         case irms_int_number:
533                 return new_tarval_from_long(0l,  mode);
534
535         case irms_reference:
536                 return new_tarval_from_long(_null_value, mode);
537         }
538         return tarval_bad;
539 }
540
541 tarval *get_tarval_one(ir_mode *mode) {
542         assert(mode);
543
544         if (get_mode_n_vector_elems(mode) > 1) {
545                 /* vector arithmetic not implemented yet */
546                 assert(0);
547                 return tarval_bad;
548         }
549
550         switch(get_mode_sort(mode)) {
551         case irms_control_flow:
552         case irms_memory:
553         case irms_auxiliary:
554                 assert(0);
555                 break;
556
557         case irms_internal_boolean:
558                 return tarval_b_true;
559
560         case irms_float_number:
561                 return new_tarval_from_double(1.0, mode);
562
563         case irms_reference:
564         case irms_int_number:
565                 return new_tarval_from_long(1l, mode);
566         }
567         return tarval_bad;
568 }
569
570 tarval *get_tarval_all_one(ir_mode *mode) {
571         assert(mode);
572
573         if (get_mode_n_vector_elems(mode) > 1) {
574                 /* vector arithmetic not implemented yet */
575                 assert(0);
576                 return tarval_bad;
577         }
578
579         switch(get_mode_sort(mode)) {
580         case irms_control_flow:
581         case irms_memory:
582         case irms_auxiliary:
583                 assert(0);
584                 return tarval_bad;
585
586         case irms_int_number:
587         case irms_internal_boolean:
588         case irms_reference:
589                 return tarval_not(get_mode_null(mode));
590
591
592         case irms_float_number:
593                 return new_tarval_from_double(1.0, mode);
594         }
595         return tarval_bad;
596 }
597
598 tarval *get_tarval_minus_one(ir_mode *mode) {
599         assert(mode);
600
601         if (get_mode_n_vector_elems(mode) > 1) {
602                 /* vector arithmetic not implemented yet */
603                 return tarval_bad;
604         }
605
606         switch(get_mode_sort(mode)) {
607         case irms_control_flow:
608         case irms_memory:
609         case irms_auxiliary:
610         case irms_internal_boolean:
611                 assert(0);
612                 break;
613
614         case irms_reference:
615                 return tarval_bad;
616
617         case irms_float_number:
618                 return mode_is_signed(mode) ? new_tarval_from_double(-1.0, mode) : tarval_bad;
619
620         case irms_int_number:
621                 return new_tarval_from_long(-1l, mode);
622         }
623         return tarval_bad;
624 }
625
626 tarval *get_tarval_nan(ir_mode *mode) {
627         assert(mode);
628
629         if (get_mode_n_vector_elems(mode) > 1) {
630                 /* vector arithmetic not implemented yet */
631                 return tarval_bad;
632         }
633
634         if (get_mode_sort(mode) == irms_float_number) {
635                 switch(get_mode_size_bits(mode)) {
636                 case 32:
637                         fc_get_qnan(8, 23, NULL);
638                         break;
639                 case 64:
640                         fc_get_qnan(11, 52, NULL);
641                         break;
642                 case 80:
643                         fc_get_qnan(15, 64, NULL);
644                         break;
645                 }
646                 return get_tarval(fc_get_buffer(), fc_get_buffer_length(), mode);
647         } else {
648                 assert(0 && "tarval is not floating point");
649                 return tarval_bad;
650         }
651 }
652
653 tarval *get_tarval_plus_inf(ir_mode *mode) {
654         assert(mode);
655
656         if (get_mode_n_vector_elems(mode) > 1) {
657                 /* vector arithmetic not implemented yet */
658                 return tarval_bad;
659         }
660
661         if (get_mode_sort(mode) == irms_float_number) {
662                 switch(get_mode_size_bits(mode)) {
663                 case 32:
664                         fc_get_plusinf(8, 23, NULL);
665                         break;
666                 case 64:
667                         fc_get_plusinf(11, 52, NULL);
668                         break;
669                 case 80:
670                         fc_get_plusinf(15, 64, NULL);
671                         break;
672                 }
673                 return get_tarval(fc_get_buffer(), fc_get_buffer_length(), mode);
674         } else {
675                 assert(0 && "tarval is not floating point");
676                 return tarval_bad;
677         }
678 }
679
680 tarval *get_tarval_minus_inf(ir_mode *mode) {
681         assert(mode);
682
683         if (get_mode_n_vector_elems(mode) > 1) {
684                 /* vector arithmetic not implemented yet */
685                 return tarval_bad;
686         }
687
688         if (get_mode_sort(mode) == irms_float_number) {
689                 switch(get_mode_size_bits(mode)) {
690                 case 32:
691                         fc_get_minusinf(8, 23, NULL);
692                         break;
693                 case 64:
694                         fc_get_minusinf(11, 52, NULL);
695                         break;
696                 case 80:
697                         fc_get_minusinf(15, 64, NULL);
698                         break;
699                 }
700                 return get_tarval(fc_get_buffer(), fc_get_buffer_length(), mode);
701         } else {
702                 assert(0 && "tarval is not floating point");
703                 return tarval_bad;
704         }
705 }
706
707 /*
708  * Arithmethic operations on tarvals ========================================
709  */
710
711 /*
712  * test if negative number, 1 means 'yes'
713  */
714 int tarval_is_negative(tarval *a) {
715         assert(a);
716
717         if (get_mode_n_vector_elems(a->mode) > 1) {
718                 /* vector arithmetic not implemented yet */
719                 assert(0 && "tarval_is_negative is not allowed for vector modes");
720                 return 0;
721         }
722
723         switch (get_mode_sort(a->mode)) {
724         case irms_int_number:
725                 if (!mode_is_signed(a->mode)) return 0;
726                 else
727                         return sc_comp(a->value, get_mode_null(a->mode)->value) == -1 ? 1 : 0;
728
729         case irms_float_number:
730                 return fc_comp(a->value, get_mode_null(a->mode)->value) == -1 ? 1 : 0;
731
732         default:
733                 assert(0 && "not implemented");
734                 return 0;
735         }
736 }
737
738 /*
739  * test if null, 1 means 'yes'
740  */
741 int tarval_is_null(tarval *a) {
742         ir_mode *m = get_tarval_mode(a);
743
744         return a == get_tarval_null(m);
745 }
746
747 /*
748  * test if one, 1 means 'yes'
749  */
750 int tarval_is_one(tarval *a) {
751         ir_mode *m = get_tarval_mode(a);
752
753         return a == get_tarval_one(m);
754 }
755
756 /*
757  * comparison
758  */
759 pn_Cmp tarval_cmp(tarval *a, tarval *b) {
760         assert(a);
761         assert(b);
762
763         if (a == tarval_bad || b == tarval_bad) {
764                 assert(0 && "Comparison with tarval_bad");
765                 return pn_Cmp_False;
766         }
767
768         if (a == tarval_undefined || b == tarval_undefined)
769                 return pn_Cmp_False;
770
771         if (a->mode != b->mode)
772                 return pn_Cmp_False;
773
774         if (get_mode_n_vector_elems(a->mode) > 1) {
775                 /* vector arithmetic not implemented yet */
776                 assert(0 && "cmp not implemented for vector modes");
777         }
778
779         /* Here the two tarvals are unequal and of the same mode */
780         switch (get_mode_sort(a->mode)) {
781         case irms_control_flow:
782         case irms_memory:
783         case irms_auxiliary:
784                 if (a == b)
785                         return pn_Cmp_Eq;
786                 return pn_Cmp_False;
787
788         case irms_float_number:
789                 if (no_float)
790                         return pn_Cmp_False;
791                 /*
792                  * BEWARE: we cannot compare a == b here, because
793                  * a NaN is always Unordered to any other value, even to itself!
794                  */
795                 switch (fc_comp(a->value, b->value)) {
796                 case -1: return pn_Cmp_Lt;
797                 case  0: return pn_Cmp_Eq;
798                 case  1: return pn_Cmp_Gt;
799                 case  2: return pn_Cmp_Uo;
800                 default: return pn_Cmp_False;
801                 }
802         case irms_reference:
803         case irms_int_number:
804                 if (a == b)
805                         return pn_Cmp_Eq;
806                 return sc_comp(a->value, b->value) == 1 ? pn_Cmp_Gt : pn_Cmp_Lt;
807
808         case irms_internal_boolean:
809                 if (a == b)
810                         return pn_Cmp_Eq;
811                 return a == tarval_b_true ? pn_Cmp_Gt : pn_Cmp_Lt;
812         }
813         return pn_Cmp_False;
814 }
815
816 /*
817  * convert to other mode
818  */
819 tarval *tarval_convert_to(tarval *src, ir_mode *dst_mode) {
820         char *buffer;
821         fp_value *res;
822
823         assert(src);
824         assert(dst_mode);
825
826         if (src->mode == dst_mode) return src;
827
828         if (get_mode_n_vector_elems(src->mode) > 1) {
829                 /* vector arithmetic not implemented yet */
830                 return tarval_bad;
831         }
832
833         switch (get_mode_sort(src->mode)) {
834         case irms_control_flow:
835         case irms_memory:
836         case irms_auxiliary:
837                 break;
838
839                 /* cast float to something */
840         case irms_float_number:
841                 switch (get_mode_sort(dst_mode)) {
842                 case irms_float_number:
843                         switch (get_mode_size_bits(dst_mode)) {
844                         case 32:
845                                 fc_cast(src->value, 8, 23, NULL);
846                                 break;
847                         case 64:
848                                 fc_cast(src->value, 11, 52, NULL);
849                                 break;
850                         case 80:
851                                 fc_cast(src->value, 15, 64, NULL);
852                                 break;
853                         default:
854                                 break;
855                         }
856                         return get_tarval(fc_get_buffer(), fc_get_buffer_length(), dst_mode);
857
858                 case irms_int_number:
859                         switch (GET_FLOAT_TO_INT_MODE()) {
860                         case TRUNCATE:
861                                 res = fc_int(src->value, NULL);
862                                 break;
863                         case ROUND:
864                                 res = fc_rnd(src->value, NULL);
865                                 break;
866                         default:
867                                 assert(0);
868                                 break;
869                         }
870                         if (! fc_flt2int(res, sc_get_buffer(), dst_mode))
871                                 return tarval_bad;
872                         return get_tarval(sc_get_buffer(), sc_get_buffer_length(), dst_mode);
873
874                 default:
875                         /* the rest can't be converted */
876                         return tarval_bad;
877                 }
878                 break;
879
880         /* cast int/characters to something */
881         case irms_int_number:
882                 switch (get_mode_sort(dst_mode)) {
883
884                 case irms_reference:
885                 case irms_int_number:
886                         buffer = alloca(sc_get_buffer_length());
887                         memcpy(buffer, src->value, sc_get_buffer_length());
888                         sign_extend(buffer, dst_mode);
889                         return get_tarval_overflow(buffer, src->length, dst_mode);
890
891                 case irms_internal_boolean:
892                         /* XXX C semantics */
893                         if (src == get_mode_null(src->mode)) return tarval_b_false;
894                         else return tarval_b_true;
895
896                 case irms_float_number:
897                         /* XXX floating point unit does not understand internal integer
898                          * representation, convert to string first, then create float from
899                          * string */
900                         buffer = alloca(100);
901                         /* decimal string representation because hexadecimal output is
902                          * interpreted unsigned by fc_val_from_str, so this is a HACK */
903                         snprintf(buffer, 100, "%s",
904                                 sc_print(src->value, get_mode_size_bits(src->mode), SC_DEC, mode_is_signed(src->mode)));
905                         buffer[100 - 1] = '\0';
906                         switch (get_mode_size_bits(dst_mode)) {
907                         case 32:
908                                 fc_val_from_str(buffer, 0, 8, 23, NULL);
909                                 break;
910                         case 64:
911                                 fc_val_from_str(buffer, 0, 11, 52, NULL);
912                                 break;
913                         case 80:
914                                 fc_val_from_str(buffer, 0, 15, 64, NULL);
915                                 break;
916                         }
917                         return get_tarval(fc_get_buffer(), fc_get_buffer_length(), dst_mode);
918
919                 default:
920                         break;
921                 }
922                 break;
923
924         case irms_internal_boolean:
925                 /* beware: this is C semantic for the INTERNAL boolean mode */
926                 if (get_mode_sort(dst_mode) == irms_int_number)
927                         return src == tarval_b_true ? get_mode_one(dst_mode) : get_mode_null(dst_mode);
928                 break;
929
930         case irms_reference:
931                 if (get_mode_sort(dst_mode) == irms_int_number) {
932                         buffer = alloca(sc_get_buffer_length());
933                         memcpy(buffer, src->value, sc_get_buffer_length());
934                         sign_extend(buffer, src->mode);
935                         return get_tarval_overflow(buffer, src->length, dst_mode);
936                 }
937                 break;
938         }
939
940         return tarval_bad;
941 }
942
943 /*
944  * bitwise negation
945  */
946 tarval *tarval_not(tarval *a) {
947         char *buffer;
948
949         assert(a);
950
951         /* works for vector mode without changes */
952
953         switch (get_mode_sort(a->mode)) {
954         case irms_reference:
955         case irms_int_number:
956                 buffer = alloca(sc_get_buffer_length());
957                 sc_not(a->value, buffer);
958                 return get_tarval(buffer, a->length, a->mode);
959
960         case irms_internal_boolean:
961                 if (a == tarval_b_true)
962                         return tarval_b_false;
963                 if (a == tarval_b_false)
964                         return tarval_b_true;
965                 return tarval_bad;
966
967         default:
968                 assert(0 && "bitwise negation is only allowed for integer and boolean");
969                 return tarval_bad;
970         }
971 }
972
973 /*
974  * arithmetic negation
975  */
976 tarval *tarval_neg(tarval *a) {
977         char *buffer;
978
979         assert(a);
980         assert(mode_is_num(a->mode)); /* negation only for numerical values */
981
982         /* note: negation is allowed even for unsigned modes. */
983
984         if (get_mode_n_vector_elems(a->mode) > 1) {
985                 /* vector arithmetic not implemented yet */
986                 return tarval_bad;
987         }
988
989         switch (get_mode_sort(a->mode)) {
990         case irms_int_number:
991                 buffer = alloca(sc_get_buffer_length());
992                 sc_neg(a->value, buffer);
993                 return get_tarval_overflow(buffer, a->length, a->mode);
994
995         case irms_float_number:
996                 if(no_float)
997                         return tarval_bad;
998
999                 fc_neg(a->value, NULL);
1000                 return get_tarval_overflow(fc_get_buffer(), fc_get_buffer_length(), a->mode);
1001
1002         default:
1003                 return tarval_bad;
1004         }
1005 }
1006
1007 /*
1008  * addition
1009  */
1010 tarval *tarval_add(tarval *a, tarval *b) {
1011         char *buffer;
1012
1013         assert(a);
1014         assert(b);
1015         assert(a->mode == b->mode);
1016
1017         if (get_mode_n_vector_elems(a->mode) > 1 || get_mode_n_vector_elems(b->mode) > 1) {
1018                 /* vector arithmetic not implemented yet */
1019                 return tarval_bad;
1020         }
1021
1022         switch (get_mode_sort(a->mode)) {
1023         case irms_int_number:
1024                 /* modes of a,b are equal, so result has mode of a as this might be the character */
1025                 buffer = alloca(sc_get_buffer_length());
1026                 sc_add(a->value, b->value, buffer);
1027                 return get_tarval_overflow(buffer, a->length, a->mode);
1028
1029         case irms_float_number:
1030                 if(no_float)
1031                         return tarval_bad;
1032
1033                 fc_add(a->value, b->value, NULL);
1034                 return get_tarval_overflow(fc_get_buffer(), fc_get_buffer_length(), a->mode);
1035
1036         default:
1037                 return tarval_bad;
1038         }
1039 }
1040
1041 /*
1042  * subtraction
1043  */
1044 tarval *tarval_sub(tarval *a, tarval *b) {
1045         char *buffer;
1046
1047         assert(a);
1048         assert(b);
1049         assert(a->mode == b->mode);
1050
1051         if (get_mode_n_vector_elems(a->mode) > 1 || get_mode_n_vector_elems(b->mode) > 1) {
1052                 /* vector arithmetic not implemented yet */
1053                 return tarval_bad;
1054         }
1055         switch (get_mode_sort(a->mode)) {
1056         case irms_int_number:
1057                 /* modes of a,b are equal, so result has mode of a as this might be the character */
1058                 buffer = alloca(sc_get_buffer_length());
1059                 sc_sub(a->value, b->value, buffer);
1060                 return get_tarval_overflow(buffer, a->length, a->mode);
1061
1062         case irms_float_number:
1063                 if(no_float)
1064                         return tarval_bad;
1065
1066                 fc_sub(a->value, b->value, NULL);
1067                 return get_tarval_overflow(fc_get_buffer(), fc_get_buffer_length(), a->mode);
1068
1069         default:
1070                 return tarval_bad;
1071         }
1072 }
1073
1074 /*
1075  * multiplication
1076  */
1077 tarval *tarval_mul(tarval *a, tarval *b) {
1078         char *buffer;
1079
1080         assert(a);
1081         assert(b);
1082         assert(a->mode == b->mode);
1083
1084         if (get_mode_n_vector_elems(a->mode) > 1) {
1085                 /* vector arithmetic not implemented yet */
1086                 return tarval_bad;
1087         }
1088
1089         switch (get_mode_sort(a->mode)) {
1090         case irms_int_number:
1091                 /* modes of a,b are equal */
1092                 buffer = alloca(sc_get_buffer_length());
1093                 sc_mul(a->value, b->value, buffer);
1094                 return get_tarval_overflow(buffer, a->length, a->mode);
1095
1096         case irms_float_number:
1097                 if(no_float)
1098                         return tarval_bad;
1099
1100                 fc_mul(a->value, b->value, NULL);
1101                 return get_tarval_overflow(fc_get_buffer(), fc_get_buffer_length(), a->mode);
1102
1103         default:
1104                 return tarval_bad;
1105         }
1106 }
1107
1108 /*
1109  * floating point division
1110  */
1111 tarval *tarval_quo(tarval *a, tarval *b) {
1112         assert(a);
1113         assert(b);
1114         assert((a->mode == b->mode) && mode_is_float(a->mode));
1115
1116         if(no_float)
1117                 return tarval_bad;
1118
1119         if (get_mode_n_vector_elems(a->mode) > 1) {
1120                 /* vector arithmetic not implemented yet */
1121                 return tarval_bad;
1122         }
1123
1124         fc_div(a->value, b->value, NULL);
1125         return get_tarval_overflow(fc_get_buffer(), fc_get_buffer_length(), a->mode);
1126 }
1127
1128 /*
1129  * integer division
1130  * overflow is impossible, but look out for division by zero
1131  */
1132 tarval *tarval_div(tarval *a, tarval *b) {
1133         assert(a);
1134         assert(b);
1135         assert((a->mode == b->mode) && mode_is_int(a->mode));
1136
1137         if (get_mode_n_vector_elems(a->mode) > 1) {
1138                 /* vector arithmetic not implemented yet */
1139                 return tarval_bad;
1140         }
1141
1142         /* x/0 error */
1143         if (b == get_mode_null(b->mode)) return tarval_bad;
1144         /* modes of a,b are equal */
1145         sc_div(a->value, b->value, NULL);
1146         return get_tarval(sc_get_buffer(), sc_get_buffer_length(), a->mode);
1147 }
1148
1149 /*
1150  * remainder
1151  * overflow is impossible, but look out for division by zero
1152  */
1153 tarval *tarval_mod(tarval *a, tarval *b) {
1154         assert(a);
1155         assert(b);
1156         assert((a->mode == b->mode) && mode_is_int(a->mode));
1157
1158         if (get_mode_n_vector_elems(a->mode) > 1) {
1159                 /* vector arithmetic not implemented yet */
1160                 return tarval_bad;
1161         }
1162
1163         /* x/0 error */
1164         if (b == get_mode_null(b->mode)) return tarval_bad;
1165         /* modes of a,b are equal */
1166         sc_mod(a->value, b->value, NULL);
1167         return get_tarval(sc_get_buffer(), sc_get_buffer_length(), a->mode);
1168 }
1169
1170 /*
1171  * integer division AND remainder
1172  * overflow is impossible, but look out for division by zero
1173  */
1174 tarval *tarval_divmod(tarval *a, tarval *b, tarval **mod) {
1175         int len = sc_get_buffer_length();
1176         char *div_res = alloca(len);
1177         char *mod_res = alloca(len);
1178
1179         assert(a);
1180         assert(b);
1181         assert((a->mode == b->mode) && mode_is_int(a->mode));
1182
1183         if (get_mode_n_vector_elems(a->mode) > 1) {
1184                 /* vector arithmetic not implemented yet */
1185                 return tarval_bad;
1186         }
1187
1188
1189         /* x/0 error */
1190         if (b == get_mode_null(b->mode)) return tarval_bad;
1191         /* modes of a,b are equal */
1192         sc_divmod(a->value, b->value, div_res, mod_res);
1193         *mod = get_tarval(mod_res, len, a->mode);
1194         return get_tarval(div_res, len, a->mode);
1195 }
1196
1197 /*
1198  * absolute value
1199  */
1200 tarval *tarval_abs(tarval *a) {
1201         char *buffer;
1202
1203         assert(a);
1204         assert(mode_is_num(a->mode));
1205
1206         if (get_mode_n_vector_elems(a->mode) > 1) {
1207                 /* vector arithmetic not implemented yet */
1208                 return tarval_bad;
1209         }
1210
1211         switch (get_mode_sort(a->mode)) {
1212         case irms_int_number:
1213                 if (sc_comp(a->value, get_mode_null(a->mode)->value) == -1) {
1214                         buffer = alloca(sc_get_buffer_length());
1215                         sc_neg(a->value, buffer);
1216                         return get_tarval_overflow(buffer, a->length, a->mode);
1217                 }
1218                 return a;
1219
1220         case irms_float_number:
1221                 if(no_float)
1222                         return tarval_bad;
1223
1224                 if (fc_comp(a->value, get_mode_null(a->mode)->value) == -1) {
1225                         fc_neg(a->value, NULL);
1226                         return get_tarval_overflow(fc_get_buffer(), fc_get_buffer_length(), a->mode);
1227                 }
1228                 return a;
1229
1230         default:
1231                 return tarval_bad;
1232         }
1233         return tarval_bad;
1234 }
1235
1236 /*
1237  * bitwise and
1238  */
1239 tarval *tarval_and(tarval *a, tarval *b) {
1240         assert(a);
1241         assert(b);
1242         assert(a->mode == b->mode);
1243
1244         /* works even for vector modes */
1245
1246         switch(get_mode_sort(a->mode)) {
1247         case irms_internal_boolean:
1248                 return (a == tarval_b_false) ? a : b;
1249
1250         case irms_int_number:
1251                 sc_and(a->value, b->value, NULL);
1252                 return get_tarval(sc_get_buffer(), sc_get_buffer_length(), a->mode);
1253
1254         default:
1255                 assert(0 && "operation not defined on mode");
1256                 return tarval_bad;
1257         }
1258 }
1259
1260 /*
1261  * bitwise or
1262  */
1263 tarval *tarval_or (tarval *a, tarval *b) {
1264         assert(a);
1265         assert(b);
1266         assert(a->mode == b->mode);
1267
1268         /* works even for vector modes */
1269
1270         switch (get_mode_sort(a->mode)) {
1271         case irms_internal_boolean:
1272                 return (a == tarval_b_true) ? a : b;
1273
1274         case irms_int_number:
1275                 sc_or(a->value, b->value, NULL);
1276                 return get_tarval(sc_get_buffer(), sc_get_buffer_length(), a->mode);
1277
1278         default:
1279                 assert(0 && "operation not defined on mode");
1280                 return tarval_bad;
1281         }
1282 }
1283
1284 /*
1285  * bitwise exclusive or (xor)
1286  */
1287 tarval *tarval_eor(tarval *a, tarval *b) {
1288         assert(a);
1289         assert(b);
1290         assert((a->mode == b->mode));
1291
1292         /* works even for vector modes */
1293
1294         switch (get_mode_sort(a->mode)) {
1295         case irms_internal_boolean:
1296                 return (a == b)? tarval_b_false : tarval_b_true;
1297
1298         case irms_int_number:
1299                 sc_xor(a->value, b->value, NULL);
1300                 return get_tarval(sc_get_buffer(), sc_get_buffer_length(), a->mode);
1301
1302         default:
1303                 assert(0 && "operation not defined on mode");
1304                 return tarval_bad;;
1305         }
1306 }
1307
1308 /*
1309  * bitwise left shift
1310  */
1311 tarval *tarval_shl(tarval *a, tarval *b) {
1312         char *temp_val = NULL;
1313
1314         assert(a);
1315         assert(b);
1316         assert(mode_is_int(a->mode) && mode_is_int(b->mode));
1317
1318         if (get_mode_n_vector_elems(a->mode) > 1 || get_mode_n_vector_elems(a->mode) > 1) {
1319                 /* vector arithmetic not implemented yet */
1320                 return tarval_bad;
1321         }
1322
1323         if (get_mode_modulo_shift(a->mode) != 0) {
1324                 temp_val = alloca(sc_get_buffer_length());
1325
1326                 sc_val_from_ulong(get_mode_modulo_shift(a->mode), temp_val);
1327                 sc_mod(b->value, temp_val, temp_val);
1328         } else
1329                 temp_val = (char*)b->value;
1330
1331         sc_shl(a->value, temp_val, get_mode_size_bits(a->mode), mode_is_signed(a->mode), NULL);
1332         return get_tarval(sc_get_buffer(), sc_get_buffer_length(), a->mode);
1333 }
1334
1335 /*
1336  * bitwise unsigned right shift
1337  */
1338 tarval *tarval_shr(tarval *a, tarval *b) {
1339         char *temp_val = NULL;
1340
1341         assert(a);
1342         assert(b);
1343         assert(mode_is_int(a->mode) && mode_is_int(b->mode));
1344
1345         if (get_mode_n_vector_elems(a->mode) > 1 || get_mode_n_vector_elems(a->mode) > 1) {
1346                 /* vector arithmetic not implemented yet */
1347                 return tarval_bad;
1348         }
1349
1350         if (get_mode_modulo_shift(a->mode) != 0) {
1351                 temp_val = alloca(sc_get_buffer_length());
1352
1353                 sc_val_from_ulong(get_mode_modulo_shift(a->mode), temp_val);
1354                 sc_mod(b->value, temp_val, temp_val);
1355         } else
1356                 temp_val = (char*)b->value;
1357
1358         sc_shr(a->value, temp_val, get_mode_size_bits(a->mode), mode_is_signed(a->mode), NULL);
1359         return get_tarval(sc_get_buffer(), sc_get_buffer_length(), a->mode);
1360 }
1361
1362 /*
1363  * bitwise signed right shift
1364  */
1365 tarval *tarval_shrs(tarval *a, tarval *b) {
1366         char *temp_val = NULL;
1367
1368         assert(a);
1369         assert(b);
1370         assert(mode_is_int(a->mode) && mode_is_int(b->mode));
1371
1372         if (get_mode_n_vector_elems(a->mode) > 1 || get_mode_n_vector_elems(a->mode) > 1) {
1373                 /* vector arithmetic not implemented yet */
1374                 return tarval_bad;
1375         }
1376
1377         if (get_mode_modulo_shift(a->mode) != 0) {
1378                 temp_val = alloca(sc_get_buffer_length());
1379
1380                 sc_val_from_ulong(get_mode_modulo_shift(a->mode), temp_val);
1381                 sc_mod(b->value, temp_val, temp_val);
1382         } else
1383                 temp_val = (char*)b->value;
1384
1385         sc_shrs(a->value, temp_val, get_mode_size_bits(a->mode), mode_is_signed(a->mode), NULL);
1386         return get_tarval(sc_get_buffer(), sc_get_buffer_length(), a->mode);
1387 }
1388
1389 /*
1390  * bitwise rotation
1391  */
1392 tarval *tarval_rot(tarval *a, tarval *b) {
1393         char *temp_val = NULL;
1394
1395         assert(a);
1396         assert(b);
1397         assert(mode_is_int(a->mode) && mode_is_int(b->mode));
1398
1399         if (get_mode_n_vector_elems(a->mode) > 1 || get_mode_n_vector_elems(a->mode) > 1) {
1400                 /* vector arithmetic not implemented yet */
1401                 return tarval_bad;
1402         }
1403
1404         if (get_mode_modulo_shift(a->mode) != 0) {
1405                 temp_val = alloca(sc_get_buffer_length());
1406
1407                 sc_val_from_ulong(get_mode_modulo_shift(a->mode), temp_val);
1408                 sc_mod(b->value, temp_val, temp_val);
1409         } else
1410                 temp_val = (char*)b->value;
1411
1412         sc_rot(a->value, temp_val, get_mode_size_bits(a->mode), mode_is_signed(a->mode), NULL);
1413         return get_tarval(sc_get_buffer(), sc_get_buffer_length(), a->mode);
1414 }
1415
1416 /*
1417  * carry flag of the last operation
1418  */
1419 int tarval_carry(void) {
1420         return sc_had_carry();
1421 }
1422
1423 /*
1424  * Output of tarvals
1425  */
1426 int tarval_snprintf(char *buf, size_t len, tarval *tv) {
1427         static const tarval_mode_info default_info = { TVO_NATIVE, NULL, NULL };
1428
1429         const char *str;
1430         char tv_buf[100];
1431         const tarval_mode_info *mode_info;
1432         const char *prefix, *suffix;
1433
1434         mode_info = tv->mode->tv_priv;
1435         if (! mode_info)
1436                 mode_info = &default_info;
1437         prefix = mode_info->mode_prefix ? mode_info->mode_prefix : "";
1438         suffix = mode_info->mode_suffix ? mode_info->mode_suffix : "";
1439
1440         switch (get_mode_sort(tv->mode)) {
1441         case irms_reference:
1442                 if (tv == tv->mode->null) return snprintf(buf, len, "NULL");
1443                 /* fall through */
1444         case irms_int_number:
1445                 switch (mode_info->mode_output) {
1446
1447                 case TVO_DECIMAL:
1448                         str = sc_print(tv->value, get_mode_size_bits(tv->mode), SC_DEC, mode_is_signed(tv->mode));
1449                         break;
1450
1451                 case TVO_OCTAL:
1452                         str = sc_print(tv->value, get_mode_size_bits(tv->mode), SC_OCT, 0);
1453                         break;
1454
1455                 case TVO_HEX:
1456                 case TVO_NATIVE:
1457                 default:
1458                         str = sc_print(tv->value, get_mode_size_bits(tv->mode), SC_HEX, 0);
1459                         break;
1460                 }
1461                 return snprintf(buf, len, "%s%s%s", prefix, str, suffix);
1462
1463         case irms_float_number:
1464                 switch (mode_info->mode_output) {
1465                 case TVO_HEX:
1466                         return snprintf(buf, len, "%s%s%s", prefix, fc_print(tv->value, tv_buf, sizeof(tv_buf), FC_PACKED), suffix);
1467
1468                 case TVO_HEXFLOAT:
1469                         return snprintf(buf, len, "%s%s%s", prefix, fc_print(tv->value, tv_buf, sizeof(tv_buf), FC_HEX), suffix);
1470
1471                 case TVO_FLOAT:
1472                 case TVO_NATIVE:
1473                 default:
1474                         return snprintf(buf, len, "%s%s%s", prefix, fc_print(tv->value, tv_buf, sizeof(tv_buf), FC_DEC), suffix);
1475                 }
1476                 break;
1477
1478         case irms_internal_boolean:
1479                 switch (mode_info->mode_output) {
1480
1481                 case TVO_DECIMAL:
1482                 case TVO_OCTAL:
1483                 case TVO_HEX:
1484                 case TVO_BINARY:
1485                         return snprintf(buf, len, "%s%c%s", prefix, (tv == tarval_b_true) ? '1' : '0', suffix);
1486
1487                 case TVO_NATIVE:
1488                 default:
1489                         return snprintf(buf, len, "%s%s%s", prefix, (tv == tarval_b_true) ? "true" : "false", suffix);
1490                 }
1491
1492         case irms_control_flow:
1493         case irms_memory:
1494         case irms_auxiliary:
1495                 return snprintf(buf, len, "<TV_OVERFLOW_BAD>");
1496         }
1497
1498         return 0;
1499 }
1500
1501 /**
1502  * Output of tarvals to stdio.
1503  */
1504 int tarval_printf(tarval *tv) {
1505         char buf[1024];
1506         int res;
1507
1508         res = tarval_snprintf(buf, sizeof(buf), tv);
1509         assert(res < (int) sizeof(buf) && "buffer to small for tarval_snprintf");
1510         printf(buf);
1511         return res;
1512 }
1513
1514 char *get_tarval_bitpattern(tarval *tv) {
1515         int i, j, pos = 0;
1516         int n = get_mode_size_bits(tv->mode);
1517         int bytes = (n + 7) / 8;
1518         char *res = xmalloc((n + 1) * sizeof(char));
1519         unsigned char byte;
1520
1521         for(i = 0; i < bytes; i++) {
1522                 byte = get_tarval_sub_bits(tv, i);
1523                 for(j = 1; j < 256; j <<= 1)
1524                         if(pos < n)
1525                                 res[pos++] = j & byte ? '1' : '0';
1526         }
1527
1528         res[n] = '\0';
1529
1530         return res;
1531 }
1532
1533 /*
1534  * access to the bitpattern
1535  */
1536 unsigned char get_tarval_sub_bits(tarval *tv, unsigned byte_ofs) {
1537         switch (get_mode_arithmetic(tv->mode)) {
1538         case irma_twos_complement:
1539                 return sc_sub_bits(tv->value, get_mode_size_bits(tv->mode), byte_ofs);
1540         case irma_ieee754:
1541                 return fc_sub_bits(tv->value, get_mode_size_bits(tv->mode), byte_ofs);
1542         default:
1543                 panic("get_tarval_sub_bits(): arithmetic mode not supported");
1544         }
1545 }
1546
1547 /*
1548  * Specify the output options of one mode.
1549  *
1550  * This functions stores the modinfo, so DO NOT DESTROY it.
1551  *
1552  * Returns zero on success.
1553  */
1554 int  set_tarval_mode_output_option(ir_mode *mode, const tarval_mode_info *modeinfo) {
1555         assert(mode);
1556
1557         mode->tv_priv = modeinfo;
1558         return 0;
1559 }
1560
1561 /*
1562  * Returns the output options of one mode.
1563  *
1564  * This functions returns the mode info of a given mode.
1565  */
1566 const tarval_mode_info *get_tarval_mode_output_option(ir_mode *mode) {
1567         assert(mode);
1568
1569         return mode->tv_priv;
1570 }
1571
1572 /*
1573  * Identifying tarvals values for algebraic simplifications.
1574  *
1575  * Returns:
1576  *   - TV_CLASSIFY_NULL    for additive neutral or the NULL tarval for reference modes,
1577  *   - TV_CLASSIFY_ONE     for multiplicative neutral,
1578  *   - TV_CLASSIFY_ALL_ONE for bitwise-and neutral
1579  *   - TV_CLASSIFY_OTHER   else
1580  */
1581 tarval_classification_t classify_tarval(tarval *tv) {
1582         if (!tv || tv == tarval_bad) return TV_CLASSIFY_OTHER;
1583
1584         if (tv == get_mode_null(tv->mode))
1585                 return TV_CLASSIFY_NULL;
1586         else if (tv == get_mode_one(tv->mode))
1587                 return TV_CLASSIFY_ONE;
1588         else if (tv == get_mode_all_one(tv->mode))
1589                 return TV_CLASSIFY_ALL_ONE;
1590
1591         return TV_CLASSIFY_OTHER;
1592 }
1593
1594 /*
1595  * Returns non-zero if a given (integer) tarval has only one single bit
1596  * set.
1597  */
1598 int tarval_is_single_bit(tarval *tv) {
1599         int i, l;
1600         int bits;
1601
1602         if (!tv || tv == tarval_bad) return 0;
1603         if (! mode_is_int(tv->mode)) return 0;
1604
1605         l = get_mode_size_bytes(tv->mode);
1606         for (bits = 0, i = l - 1; i >= 0; --i) {
1607                 unsigned char v = get_tarval_sub_bits(tv, (unsigned)i);
1608
1609                 /* check for more than one bit in these */
1610                 if (v) {
1611                         if (v & (v-1))
1612                                 return 0;
1613                         if (++bits > 1)
1614                                 return 0;
1615                 }
1616         }
1617         return bits;
1618 }
1619
1620 /*
1621  * Returns non-zero if the mantissa of a floating point IEEE-754
1622  * tarval is zero (i.e. 1.0Exxx)
1623  */
1624 int tarval_ieee754_zero_mantissa(tarval *tv) {
1625         assert(get_mode_arithmetic(tv->mode) == irma_ieee754);
1626         return fc_zero_mantissa(tv->value);
1627 }
1628
1629 /* Returns the exponent of a floating point IEEE-754 tarval. */
1630 int tarval_ieee754_get_exponent(tarval *tv) {
1631         assert(get_mode_arithmetic(tv->mode) == irma_ieee754);
1632         return fc_get_exponent(tv->value);
1633 }
1634
1635 /* Set the immediate precision for IEEE-754 results. */
1636 unsigned tarval_ieee754_set_immediate_precision(unsigned bits) {
1637         return fc_set_immediate_precision(bits);
1638 }
1639
1640 /* Returns non-zero if the result of the last IEEE-754 operation was exact. */
1641 unsigned tarval_ieee754_get_exact(void) {
1642         return fc_is_exact();
1643 }
1644
1645 /*
1646  * Sets the overflow mode for integer operations.
1647  */
1648 void tarval_set_integer_overflow_mode(tarval_int_overflow_mode_t ov_mode) {
1649         int_overflow_mode = ov_mode;
1650 }
1651
1652 /* Get the overflow mode for integer operations. */
1653 tarval_int_overflow_mode_t tarval_get_integer_overflow_mode(void) {
1654         return int_overflow_mode;
1655 }
1656
1657 /* Enable/Disable floating point constant folding. */
1658 int tarval_enable_fp_ops(int enable) {
1659         int old = !no_float;
1660
1661         no_float = !enable;
1662         return old;
1663 }
1664
1665 /**
1666  * default mode_info for output as HEX
1667  */
1668 static const tarval_mode_info hex_output = {
1669         TVO_HEX,
1670         "0x",
1671         NULL,
1672 };
1673
1674 /*
1675  * Initialization of the tarval module: called before init_mode()
1676  */
1677 void init_tarval_1(long null_value) {
1678         _null_value = null_value;
1679
1680         /* initialize the sets holding the tarvals with a comparison function and
1681          * an initial size, which is the expected number of constants */
1682         tarvals = new_set(memcmp, N_CONSTANTS);
1683         values  = new_set(memcmp, N_CONSTANTS);
1684         /* init strcalc with precision of 68 to support floating point values with 64
1685          * bit mantissa (needs extra bits for rounding and overflow) */
1686         init_strcalc(68);
1687         init_fltcalc(0);
1688 }
1689
1690 /*
1691  * Initialization of the tarval module: called after init_mode()
1692  */
1693 void init_tarval_2(void) {
1694         tarval_bad->kind        = k_tarval;
1695         tarval_bad->mode        = mode_BAD;
1696         tarval_bad->value       = INT_TO_PTR(resid_tarval_bad);
1697
1698         tarval_undefined->kind  = k_tarval;
1699         tarval_undefined->mode  = mode_ANY;
1700         tarval_undefined->value = INT_TO_PTR(resid_tarval_undefined);
1701
1702         tarval_b_true->kind     = k_tarval;
1703         tarval_b_true->mode     = mode_b;
1704         tarval_b_true->value    = INT_TO_PTR(resid_tarval_b_true);
1705
1706         tarval_b_false->kind    = k_tarval;
1707         tarval_b_false->mode    = mode_b;
1708         tarval_b_false->value   = INT_TO_PTR(resid_tarval_b_false);
1709
1710         /*
1711          * assign output modes that are compatible with the
1712          * old implementation: Hex output
1713          */
1714         set_tarval_mode_output_option(mode_Bs, &hex_output);
1715         set_tarval_mode_output_option(mode_Bu, &hex_output);
1716         set_tarval_mode_output_option(mode_Hs, &hex_output);
1717         set_tarval_mode_output_option(mode_Hu, &hex_output);
1718         set_tarval_mode_output_option(mode_Is, &hex_output);
1719         set_tarval_mode_output_option(mode_Iu, &hex_output);
1720         set_tarval_mode_output_option(mode_Ls, &hex_output);
1721         set_tarval_mode_output_option(mode_Lu, &hex_output);
1722         set_tarval_mode_output_option(mode_P,  &hex_output);
1723 }
1724
1725 /* free all memory occupied by tarval. */
1726 void finish_tarval(void) {
1727         finish_strcalc();
1728         finish_fltcalc();
1729         del_set(tarvals); tarvals = NULL;
1730         del_set(values);  values = NULL;
1731 }
1732
1733 /****************************************************************************
1734  *   end of tv.c
1735  ****************************************************************************/