00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071 #include "proj.h"
00072 #include "glimits.h"
00073 #include "target.h"
00074 #include "diagnostic.h"
00075 #include "bad.h"
00076 #include "info.h"
00077 #include "lex.h"
00078 #include "malloc.h"
00079
00080
00081
00082 char ffetarget_string_[40];
00083 HOST_WIDE_INT ffetarget_long_val_;
00084 HOST_WIDE_INT ffetarget_long_junk_;
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096
00097
00098
00099
00100
00101
00102
00103 static void ffetarget_print_char_ (FILE *f, unsigned char c);
00104
00105
00106
00107 #ifdef REAL_VALUE_ATOF
00108 #define FFETARGET_ATOF_(p,m) REAL_VALUE_ATOF ((p),(m))
00109 #else
00110 #define FFETARGET_ATOF_(p,m) atof ((p))
00111 #endif
00112
00113
00114
00115
00116
00117
00118
00119
00120 static void
00121 ffetarget_print_char_ (FILE *f, unsigned char c)
00122 {
00123 switch (c)
00124 {
00125 case '\\':
00126 fputs ("\\\\", f);
00127 break;
00128
00129 case '\'':
00130 fputs ("\\\'", f);
00131 break;
00132
00133 default:
00134 if (ISPRINT (c))
00135 fputc (c, f);
00136 else
00137 fprintf (f, "\\%03o", (unsigned int) c);
00138 break;
00139 }
00140 }
00141
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154
00155
00156
00157
00158
00159
00160
00161
00162
00163
00164
00165
00166 void
00167 ffetarget_aggregate_info (ffeinfoBasictype *ebt, ffeinfoKindtype *ekt,
00168 ffetargetAlign *units, ffeinfoBasictype abt,
00169 ffeinfoKindtype akt)
00170 {
00171 ffetype type;
00172
00173 if ((abt == FFEINFO_basictypeNONE) || (abt == FFEINFO_basictypeANY)
00174 || (akt == FFEINFO_kindtypeNONE))
00175 {
00176 *ebt = FFEINFO_basictypeCHARACTER;
00177 *ekt = FFEINFO_kindtypeCHARACTERDEFAULT;
00178 }
00179 else
00180 {
00181 *ebt = abt;
00182 *ekt = akt;
00183 }
00184
00185 type = ffeinfo_type (*ebt, *ekt);
00186 assert (type != NULL);
00187
00188 *units = ffetype_size (type);
00189 }
00190
00191
00192
00193
00194
00195
00196
00197
00198
00199
00200
00201
00202 ffetargetAlign
00203 ffetarget_align (ffetargetAlign *updated_alignment,
00204 ffetargetAlign *updated_modulo, ffetargetOffset offset,
00205 ffetargetAlign alignment, ffetargetAlign modulo)
00206 {
00207 ffetargetAlign pad;
00208 ffetargetAlign min_pad;
00209 ffetargetAlign min_m = 0;
00210 ffetargetAlign ua;
00211 ffetargetAlign um;
00212 ffetargetAlign ucnt;
00213 ffetargetAlign m;
00214 ffetargetAlign cnt;
00215 ffetargetAlign i;
00216 ffetargetAlign j;
00217
00218 assert (alignment > 0);
00219 assert (*updated_alignment > 0);
00220
00221 assert (*updated_modulo < *updated_alignment);
00222 assert (modulo < alignment);
00223
00224
00225 if (*updated_alignment == alignment)
00226 {
00227 if (modulo > *updated_modulo)
00228 pad = alignment - (modulo - *updated_modulo);
00229 else
00230 pad = *updated_modulo - modulo;
00231 if (offset < 0)
00232
00233 offset = alignment - ((- offset) % alignment);
00234 pad = (offset + pad) % alignment;
00235 if (pad != 0)
00236 pad = alignment - pad;
00237 return pad;
00238 }
00239
00240
00241
00242 for (ua = *updated_alignment, ucnt = 1;
00243 ua % alignment != 0;
00244 ua += *updated_alignment)
00245 ++ucnt;
00246
00247 cnt = ua / alignment;
00248
00249 if (offset < 0)
00250
00251 offset = ua - ((- offset) % ua);
00252
00253
00254 min_pad = ~(ffetargetAlign) 0;
00255
00256
00257
00258
00259
00260
00261 for (um = *updated_modulo, i = 0; i < ucnt; um += *updated_alignment, ++i)
00262 {
00263 for (m = modulo, j = 0; j < cnt; m += alignment, ++j)
00264 {
00265
00266 if (m > um)
00267 pad = ua - (m - um);
00268 else
00269 pad = um - m;
00270 pad = (offset + pad) % ua;
00271 if (pad == 0)
00272 {
00273
00274 *updated_alignment = ua;
00275 *updated_modulo = um;
00276 return 0;
00277 }
00278 pad = ua - pad;
00279 if (pad < min_pad)
00280 {
00281 min_pad = pad;
00282 min_m = um;
00283 }
00284 }
00285 }
00286
00287 *updated_alignment = ua;
00288 *updated_modulo = min_m;
00289 return min_pad;
00290 }
00291
00292
00293
00294
00295
00296
00297
00298
00299 #if FFETARGET_okCHARACTER1
00300 bool
00301 ffetarget_character1 (ffetargetCharacter1 *val, ffelexToken character,
00302 mallocPool pool)
00303 {
00304 val->length = ffelex_token_length (character);
00305 if (val->length == 0)
00306 val->text = NULL;
00307 else
00308 {
00309 val->text = malloc_new_kp (pool, "ffetargetCharacter1", val->length + 1);
00310 memcpy (val->text, ffelex_token_text (character), val->length);
00311 val->text[val->length] = '\0';
00312 }
00313
00314 return TRUE;
00315 }
00316
00317 #endif
00318
00319
00320
00321
00322 #if FFETARGET_okCHARACTER1
00323 int
00324 ffetarget_cmp_character1 (ffetargetCharacter1 l, ffetargetCharacter1 r)
00325 {
00326 if (l.length < r.length)
00327 return -1;
00328 if (l.length > r.length)
00329 return 1;
00330 if (l.length == 0)
00331 return 0;
00332 return memcmp (l.text, r.text, l.length);
00333 }
00334
00335 #endif
00336
00337
00338
00339
00340
00341
00342
00343
00344
00345 #if FFETARGET_okCHARACTER1
00346 ffebad
00347 ffetarget_concatenate_character1 (ffetargetCharacter1 *res,
00348 ffetargetCharacter1 l, ffetargetCharacter1 r, mallocPool pool,
00349 ffetargetCharacterSize *len)
00350 {
00351 res->length = *len = l.length + r.length;
00352 if (*len == 0)
00353 res->text = NULL;
00354 else
00355 {
00356 res->text = malloc_new_kp (pool, "ffetargetCharacter1(CONCAT)", *len + 1);
00357 if (l.length != 0)
00358 memcpy (res->text, l.text, l.length);
00359 if (r.length != 0)
00360 memcpy (res->text + l.length, r.text, r.length);
00361 res->text[*len] = '\0';
00362 }
00363
00364 return FFEBAD;
00365 }
00366
00367 #endif
00368
00369
00370
00371
00372 #if FFETARGET_okCHARACTER1
00373 ffebad
00374 ffetarget_eq_character1 (bool *res, ffetargetCharacter1 l,
00375 ffetargetCharacter1 r)
00376 {
00377 assert (l.length == r.length);
00378 *res = (memcmp (l.text, r.text, l.length) == 0);
00379 return FFEBAD;
00380 }
00381
00382 #endif
00383
00384
00385
00386
00387 #if FFETARGET_okCHARACTER1
00388 ffebad
00389 ffetarget_le_character1 (bool *res, ffetargetCharacter1 l,
00390 ffetargetCharacter1 r)
00391 {
00392 assert (l.length == r.length);
00393 *res = (memcmp (l.text, r.text, l.length) <= 0);
00394 return FFEBAD;
00395 }
00396
00397 #endif
00398
00399
00400
00401
00402 #if FFETARGET_okCHARACTER1
00403 ffebad
00404 ffetarget_lt_character1 (bool *res, ffetargetCharacter1 l,
00405 ffetargetCharacter1 r)
00406 {
00407 assert (l.length == r.length);
00408 *res = (memcmp (l.text, r.text, l.length) < 0);
00409 return FFEBAD;
00410 }
00411
00412 #endif
00413
00414
00415
00416
00417 #if FFETARGET_okCHARACTER1
00418 ffebad
00419 ffetarget_ge_character1 (bool *res, ffetargetCharacter1 l,
00420 ffetargetCharacter1 r)
00421 {
00422 assert (l.length == r.length);
00423 *res = (memcmp (l.text, r.text, l.length) >= 0);
00424 return FFEBAD;
00425 }
00426
00427 #endif
00428
00429
00430
00431
00432 #if FFETARGET_okCHARACTER1
00433 ffebad
00434 ffetarget_gt_character1 (bool *res, ffetargetCharacter1 l,
00435 ffetargetCharacter1 r)
00436 {
00437 assert (l.length == r.length);
00438 *res = (memcmp (l.text, r.text, l.length) > 0);
00439 return FFEBAD;
00440 }
00441 #endif
00442
00443 #if FFETARGET_okCHARACTER1
00444 bool
00445 ffetarget_iszero_character1 (ffetargetCharacter1 constant)
00446 {
00447 ffetargetCharacterSize i;
00448
00449 for (i = 0; i < constant.length; ++i)
00450 if (constant.text[i] != 0)
00451 return FALSE;
00452 return TRUE;
00453 }
00454 #endif
00455
00456 bool
00457 ffetarget_iszero_hollerith (ffetargetHollerith constant)
00458 {
00459 ffetargetHollerithSize i;
00460
00461 for (i = 0; i < constant.length; ++i)
00462 if (constant.text[i] != 0)
00463 return FALSE;
00464 return TRUE;
00465 }
00466
00467
00468
00469
00470
00471
00472 void
00473 ffetarget_layout (const char *error_text UNUSED, ffetargetAlign *alignment,
00474 ffetargetAlign *modulo, ffetargetOffset *size,
00475 ffeinfoBasictype bt, ffeinfoKindtype kt,
00476 ffetargetCharacterSize charsize,
00477 ffetargetIntegerDefault num_elements)
00478 {
00479 bool ok;
00480 ffetargetOffset numele;
00481 ffetype type;
00482
00483 type = ffeinfo_type (bt, kt);
00484 assert (type != NULL);
00485
00486 *alignment = ffetype_alignment (type);
00487 *modulo = ffetype_modulo (type);
00488 if (bt == FFEINFO_basictypeCHARACTER)
00489 {
00490 ok = ffetarget_offset_charsize (size, charsize, ffetype_size (type));
00491 #ifdef ffetarget_offset_overflow
00492 if (!ok)
00493 ffetarget_offset_overflow (error_text);
00494 #endif
00495 }
00496 else
00497 *size = ffetype_size (type);
00498
00499 if ((num_elements < 0)
00500 || !ffetarget_offset (&numele, num_elements)
00501 || !ffetarget_offset_multiply (size, *size, numele))
00502 {
00503 ffetarget_offset_overflow (error_text);
00504 *alignment = 1;
00505 *modulo = 0;
00506 *size = 0;
00507 }
00508 }
00509
00510
00511
00512
00513
00514 #if FFETARGET_okCHARACTER1
00515 ffebad
00516 ffetarget_ne_character1 (bool *res, ffetargetCharacter1 l,
00517 ffetargetCharacter1 r)
00518 {
00519 assert (l.length == r.length);
00520 *res = (memcmp (l.text, r.text, l.length) != 0);
00521 return FFEBAD;
00522 }
00523
00524 #endif
00525
00526
00527
00528
00529
00530
00531
00532
00533
00534 #if FFETARGET_okCHARACTER1
00535 ffebad
00536 ffetarget_substr_character1 (ffetargetCharacter1 *res,
00537 ffetargetCharacter1 l,
00538 ffetargetCharacterSize first,
00539 ffetargetCharacterSize last, mallocPool pool,
00540 ffetargetCharacterSize *len)
00541 {
00542 if (last < first)
00543 {
00544 res->length = *len = 0;
00545 res->text = NULL;
00546 }
00547 else
00548 {
00549 res->length = *len = last - first + 1;
00550 res->text = malloc_new_kp (pool, "ffetargetCharacter1(SUBSTR)", *len + 1);
00551 memcpy (res->text, l.text + first - 1, *len);
00552 res->text[*len] = '\0';
00553 }
00554
00555 return FFEBAD;
00556 }
00557
00558 #endif
00559
00560
00561
00562
00563
00564 int
00565 ffetarget_cmp_hollerith (ffetargetHollerith l, ffetargetHollerith r)
00566 {
00567 if (l.length < r.length)
00568 return -1;
00569 if (l.length > r.length)
00570 return 1;
00571 return memcmp (l.text, r.text, l.length);
00572 }
00573
00574 ffebad
00575 ffetarget_convert_any_character1_ (char *res, size_t size,
00576 ffetargetCharacter1 l)
00577 {
00578 if (size <= (size_t) l.length)
00579 {
00580 char *p;
00581 ffetargetCharacterSize i;
00582
00583 memcpy (res, l.text, size);
00584 for (p = &l.text[0] + size, i = l.length - size;
00585 i > 0;
00586 ++p, --i)
00587 if (*p != ' ')
00588 return FFEBAD_TRUNCATING_CHARACTER;
00589 }
00590 else
00591 {
00592 memcpy (res, l.text, size);
00593 memset (res + l.length, ' ', size - l.length);
00594 }
00595
00596 return FFEBAD;
00597 }
00598
00599 ffebad
00600 ffetarget_convert_any_hollerith_ (char *res, size_t size,
00601 ffetargetHollerith l)
00602 {
00603 if (size <= (size_t) l.length)
00604 {
00605 char *p;
00606 ffetargetCharacterSize i;
00607
00608 memcpy (res, l.text, size);
00609 for (p = &l.text[0] + size, i = l.length - size;
00610 i > 0;
00611 ++p, --i)
00612 if (*p != ' ')
00613 return FFEBAD_TRUNCATING_HOLLERITH;
00614 }
00615 else
00616 {
00617 memcpy (res, l.text, size);
00618 memset (res + l.length, ' ', size - l.length);
00619 }
00620
00621 return FFEBAD;
00622 }
00623
00624 ffebad
00625 ffetarget_convert_any_typeless_ (char *res, size_t size,
00626 ffetargetTypeless l)
00627 {
00628 unsigned long long int l1;
00629 unsigned long int l2;
00630 unsigned int l3;
00631 unsigned short int l4;
00632 unsigned char l5;
00633 size_t size_of;
00634 char *p;
00635
00636 if (size >= sizeof (l1))
00637 {
00638 l1 = l;
00639 p = (char *) &l1;
00640 size_of = sizeof (l1);
00641 }
00642 else if (size >= sizeof (l2))
00643 {
00644 l2 = l;
00645 p = (char *) &l2;
00646 size_of = sizeof (l2);
00647 l1 = l2;
00648 }
00649 else if (size >= sizeof (l3))
00650 {
00651 l3 = l;
00652 p = (char *) &l3;
00653 size_of = sizeof (l3);
00654 l1 = l3;
00655 }
00656 else if (size >= sizeof (l4))
00657 {
00658 l4 = l;
00659 p = (char *) &l4;
00660 size_of = sizeof (l4);
00661 l1 = l4;
00662 }
00663 else if (size >= sizeof (l5))
00664 {
00665 l5 = l;
00666 p = (char *) &l5;
00667 size_of = sizeof (l5);
00668 l1 = l5;
00669 }
00670 else
00671 {
00672 assert ("stumped by conversion from typeless!" == NULL);
00673 abort ();
00674 }
00675
00676 if (size <= size_of)
00677 {
00678 int i = size_of - size;
00679
00680 memcpy (res, p + i, size);
00681 for (; i > 0; ++p, --i)
00682 if (*p != '\0')
00683 return FFEBAD_TRUNCATING_TYPELESS;
00684 }
00685 else
00686 {
00687 int i = size - size_of;
00688
00689 memset (res, 0, i);
00690 memcpy (res + i, p, size_of);
00691 }
00692
00693 if (l1 != l)
00694 return FFEBAD_TRUNCATING_TYPELESS;
00695 return FFEBAD;
00696 }
00697
00698
00699
00700
00701
00702
00703
00704
00705 #if FFETARGET_okCHARACTER1
00706 ffebad
00707 ffetarget_convert_character1_character1 (ffetargetCharacter1 *res,
00708 ffetargetCharacterSize size,
00709 ffetargetCharacter1 l,
00710 mallocPool pool)
00711 {
00712 res->length = size;
00713 if (size == 0)
00714 res->text = NULL;
00715 else
00716 {
00717 res->text = malloc_new_kp (pool, "FFETARGET cvt char1", size + 1);
00718 if (size <= l.length)
00719 memcpy (res->text, l.text, size);
00720 else
00721 {
00722 memcpy (res->text, l.text, l.length);
00723 memset (res->text + l.length, ' ', size - l.length);
00724 }
00725 res->text[size] = '\0';
00726 }
00727
00728 return FFEBAD;
00729 }
00730
00731 #endif
00732
00733
00734
00735
00736
00737
00738
00739
00740 #if FFETARGET_okCHARACTER1
00741 ffebad
00742 ffetarget_convert_character1_hollerith (ffetargetCharacter1 *res,
00743 ffetargetCharacterSize size,
00744 ffetargetHollerith l, mallocPool pool)
00745 {
00746 res->length = size;
00747 if (size == 0)
00748 res->text = NULL;
00749 else
00750 {
00751 res->text = malloc_new_kp (pool, "FFETARGET cvt char1", size + 1);
00752 res->text[size] = '\0';
00753 if (size <= l.length)
00754 {
00755 char *p;
00756 ffetargetCharacterSize i;
00757
00758 memcpy (res->text, l.text, size);
00759 for (p = &l.text[0] + size, i = l.length - size;
00760 i > 0;
00761 ++p, --i)
00762 if (*p != ' ')
00763 return FFEBAD_TRUNCATING_HOLLERITH;
00764 }
00765 else
00766 {
00767 memcpy (res->text, l.text, l.length);
00768 memset (res->text + l.length, ' ', size - l.length);
00769 }
00770 }
00771
00772 return FFEBAD;
00773 }
00774
00775 #endif
00776
00777
00778
00779
00780
00781
00782
00783
00784
00785 #if FFETARGET_okCHARACTER1
00786 ffebad
00787 ffetarget_convert_character1_integer4 (ffetargetCharacter1 *res,
00788 ffetargetCharacterSize size,
00789 ffetargetInteger4 l, mallocPool pool)
00790 {
00791 long long int l1;
00792 long int l2;
00793 int l3;
00794 short int l4;
00795 char l5;
00796 size_t size_of;
00797 char *p;
00798
00799 if (((size_t) size) >= sizeof (l1))
00800 {
00801 l1 = l;
00802 p = (char *) &l1;
00803 size_of = sizeof (l1);
00804 }
00805 else if (((size_t) size) >= sizeof (l2))
00806 {
00807 l2 = l;
00808 p = (char *) &l2;
00809 size_of = sizeof (l2);
00810 l1 = l2;
00811 }
00812 else if (((size_t) size) >= sizeof (l3))
00813 {
00814 l3 = l;
00815 p = (char *) &l3;
00816 size_of = sizeof (l3);
00817 l1 = l3;
00818 }
00819 else if (((size_t) size) >= sizeof (l4))
00820 {
00821 l4 = l;
00822 p = (char *) &l4;
00823 size_of = sizeof (l4);
00824 l1 = l4;
00825 }
00826 else if (((size_t) size) >= sizeof (l5))
00827 {
00828 l5 = l;
00829 p = (char *) &l5;
00830 size_of = sizeof (l5);
00831 l1 = l5;
00832 }
00833 else
00834 {
00835 assert ("stumped by conversion from integer1!" == NULL);
00836 abort ();
00837 }
00838
00839 res->length = size;
00840 if (size == 0)
00841 res->text = NULL;
00842 else
00843 {
00844 res->text = malloc_new_kp (pool, "FFETARGET cvt char1", size + 1);
00845 res->text[size] = '\0';
00846 if (((size_t) size) <= size_of)
00847 {
00848 int i = size_of - size;
00849
00850 memcpy (res->text, p + i, size);
00851 for (; i > 0; ++p, --i)
00852 if (*p != 0)
00853 return FFEBAD_TRUNCATING_NUMERIC;
00854 }
00855 else
00856 {
00857 int i = size - size_of;
00858
00859 memset (res->text, 0, i);
00860 memcpy (res->text + i, p, size_of);
00861 }
00862 }
00863
00864 if (l1 != l)
00865 return FFEBAD_TRUNCATING_NUMERIC;
00866 return FFEBAD;
00867 }
00868
00869 #endif
00870
00871
00872
00873
00874
00875
00876
00877
00878
00879 #if FFETARGET_okCHARACTER1
00880 ffebad
00881 ffetarget_convert_character1_logical4 (ffetargetCharacter1 *res,
00882 ffetargetCharacterSize size,
00883 ffetargetLogical4 l, mallocPool pool)
00884 {
00885 long long int l1;
00886 long int l2;
00887 int l3;
00888 short int l4;
00889 char l5;
00890 size_t size_of;
00891 char *p;
00892
00893 if (((size_t) size) >= sizeof (l1))
00894 {
00895 l1 = l;
00896 p = (char *) &l1;
00897 size_of = sizeof (l1);
00898 }
00899 else if (((size_t) size) >= sizeof (l2))
00900 {
00901 l2 = l;
00902 p = (char *) &l2;
00903 size_of = sizeof (l2);
00904 l1 = l2;
00905 }
00906 else if (((size_t) size) >= sizeof (l3))
00907 {
00908 l3 = l;
00909 p = (char *) &l3;
00910 size_of = sizeof (l3);
00911 l1 = l3;
00912 }
00913 else if (((size_t) size) >= sizeof (l4))
00914 {
00915 l4 = l;
00916 p = (char *) &l4;
00917 size_of = sizeof (l4);
00918 l1 = l4;
00919 }
00920 else if (((size_t) size) >= sizeof (l5))
00921 {
00922 l5 = l;
00923 p = (char *) &l5;
00924 size_of = sizeof (l5);
00925 l1 = l5;
00926 }
00927 else
00928 {
00929 assert ("stumped by conversion from logical1!" == NULL);
00930 abort ();
00931 }
00932
00933 res->length = size;
00934 if (size == 0)
00935 res->text = NULL;
00936 else
00937 {
00938 res->text = malloc_new_kp (pool, "FFETARGET cvt char1", size + 1);
00939 res->text[size] = '\0';
00940 if (((size_t) size) <= size_of)
00941 {
00942 int i = size_of - size;
00943
00944 memcpy (res->text, p + i, size);
00945 for (; i > 0; ++p, --i)
00946 if (*p != 0)
00947 return FFEBAD_TRUNCATING_NUMERIC;
00948 }
00949 else
00950 {
00951 int i = size - size_of;
00952
00953 memset (res->text, 0, i);
00954 memcpy (res->text + i, p, size_of);
00955 }
00956 }
00957
00958 if (l1 != l)
00959 return FFEBAD_TRUNCATING_NUMERIC;
00960 return FFEBAD;
00961 }
00962
00963 #endif
00964
00965
00966
00967
00968
00969
00970
00971
00972
00973 #if FFETARGET_okCHARACTER1
00974 ffebad
00975 ffetarget_convert_character1_typeless (ffetargetCharacter1 *res,
00976 ffetargetCharacterSize size,
00977 ffetargetTypeless l, mallocPool pool)
00978 {
00979 unsigned long long int l1;
00980 unsigned long int l2;
00981 unsigned int l3;
00982 unsigned short int l4;
00983 unsigned char l5;
00984 size_t size_of;
00985 char *p;
00986
00987 if (((size_t) size) >= sizeof (l1))
00988 {
00989 l1 = l;
00990 p = (char *) &l1;
00991 size_of = sizeof (l1);
00992 }
00993 else if (((size_t) size) >= sizeof (l2))
00994 {
00995 l2 = l;
00996 p = (char *) &l2;
00997 size_of = sizeof (l2);
00998 l1 = l2;
00999 }
01000 else if (((size_t) size) >= sizeof (l3))
01001 {
01002 l3 = l;
01003 p = (char *) &l3;
01004 size_of = sizeof (l3);
01005 l1 = l3;
01006 }
01007 else if (((size_t) size) >= sizeof (l4))
01008 {
01009 l4 = l;
01010 p = (char *) &l4;
01011 size_of = sizeof (l4);
01012 l1 = l4;
01013 }
01014 else if (((size_t) size) >= sizeof (l5))
01015 {
01016 l5 = l;
01017 p = (char *) &l5;
01018 size_of = sizeof (l5);
01019 l1 = l5;
01020 }
01021 else
01022 {
01023 assert ("stumped by conversion from typeless!" == NULL);
01024 abort ();
01025 }
01026
01027 res->length = size;
01028 if (size == 0)
01029 res->text = NULL;
01030 else
01031 {
01032 res->text = malloc_new_kp (pool, "FFETARGET cvt char1", size + 1);
01033 res->text[size] = '\0';
01034 if (((size_t) size) <= size_of)
01035 {
01036 int i = size_of - size;
01037
01038 memcpy (res->text, p + i, size);
01039 for (; i > 0; ++p, --i)
01040 if (*p != 0)
01041 return FFEBAD_TRUNCATING_TYPELESS;
01042 }
01043 else
01044 {
01045 int i = size - size_of;
01046
01047 memset (res->text, 0, i);
01048 memcpy (res->text + i, p, size_of);
01049 }
01050 }
01051
01052 if (l1 != l)
01053 return FFEBAD_TRUNCATING_TYPELESS;
01054 return FFEBAD;
01055 }
01056
01057 #endif
01058
01059
01060
01061
01062 #if FFETARGET_okCOMPLEX1
01063 ffebad
01064 ffetarget_divide_complex1 (ffetargetComplex1 *res, ffetargetComplex1 l,
01065 ffetargetComplex1 r)
01066 {
01067 ffebad bad;
01068 ffetargetReal1 tmp1, tmp2, tmp3, tmp4;
01069
01070 bad = ffetarget_multiply_real1 (&tmp1, r.real, r.real);
01071 if (bad != FFEBAD)
01072 return bad;
01073 bad = ffetarget_multiply_real1 (&tmp2, r.imaginary, r.imaginary);
01074 if (bad != FFEBAD)
01075 return bad;
01076 bad = ffetarget_add_real1 (&tmp3, tmp1, tmp2);
01077 if (bad != FFEBAD)
01078 return bad;
01079
01080 if (ffetarget_iszero_real1 (tmp3))
01081 {
01082 ffetarget_real1_zero (&(res)->real);
01083 ffetarget_real1_zero (&(res)->imaginary);
01084 return FFEBAD_DIV_BY_ZERO;
01085 }
01086
01087 bad = ffetarget_multiply_real1 (&tmp1, l.real, r.real);
01088 if (bad != FFEBAD)
01089 return bad;
01090 bad = ffetarget_multiply_real1 (&tmp2, l.imaginary, r.imaginary);
01091 if (bad != FFEBAD)
01092 return bad;
01093 bad = ffetarget_add_real1 (&tmp4, tmp1, tmp2);
01094 if (bad != FFEBAD)
01095 return bad;
01096 bad = ffetarget_divide_real1 (&res->real, tmp4, tmp3);
01097 if (bad != FFEBAD)
01098 return bad;
01099
01100 bad = ffetarget_multiply_real1 (&tmp1, r.real, l.imaginary);
01101 if (bad != FFEBAD)
01102 return bad;
01103 bad = ffetarget_multiply_real1 (&tmp2, l.real, r.imaginary);
01104 if (bad != FFEBAD)
01105 return bad;
01106 bad = ffetarget_subtract_real1 (&tmp4, tmp1, tmp2);
01107 if (bad != FFEBAD)
01108 return bad;
01109 bad = ffetarget_divide_real1 (&res->imaginary, tmp4, tmp3);
01110
01111 return FFEBAD;
01112 }
01113
01114 #endif
01115
01116
01117
01118
01119 #if FFETARGET_okCOMPLEX2
01120 ffebad
01121 ffetarget_divide_complex2 (ffetargetComplex2 *res, ffetargetComplex2 l,
01122 ffetargetComplex2 r)
01123 {
01124 ffebad bad;
01125 ffetargetReal2 tmp1, tmp2, tmp3, tmp4;
01126
01127 bad = ffetarget_multiply_real2 (&tmp1, r.real, r.real);
01128 if (bad != FFEBAD)
01129 return bad;
01130 bad = ffetarget_multiply_real2 (&tmp2, r.imaginary, r.imaginary);
01131 if (bad != FFEBAD)
01132 return bad;
01133 bad = ffetarget_add_real2 (&tmp3, tmp1, tmp2);
01134 if (bad != FFEBAD)
01135 return bad;
01136
01137 if (ffetarget_iszero_real2 (tmp3))
01138 {
01139 ffetarget_real2_zero (&(res)->real);
01140 ffetarget_real2_zero (&(res)->imaginary);
01141 return FFEBAD_DIV_BY_ZERO;
01142 }
01143
01144 bad = ffetarget_multiply_real2 (&tmp1, l.real, r.real);
01145 if (bad != FFEBAD)
01146 return bad;
01147 bad = ffetarget_multiply_real2 (&tmp2, l.imaginary, r.imaginary);
01148 if (bad != FFEBAD)
01149 return bad;
01150 bad = ffetarget_add_real2 (&tmp4, tmp1, tmp2);
01151 if (bad != FFEBAD)
01152 return bad;
01153 bad = ffetarget_divide_real2 (&res->real, tmp4, tmp3);
01154 if (bad != FFEBAD)
01155 return bad;
01156
01157 bad = ffetarget_multiply_real2 (&tmp1, r.real, l.imaginary);
01158 if (bad != FFEBAD)
01159 return bad;
01160 bad = ffetarget_multiply_real2 (&tmp2, l.real, r.imaginary);
01161 if (bad != FFEBAD)
01162 return bad;
01163 bad = ffetarget_subtract_real2 (&tmp4, tmp1, tmp2);
01164 if (bad != FFEBAD)
01165 return bad;
01166 bad = ffetarget_divide_real2 (&res->imaginary, tmp4, tmp3);
01167
01168 return FFEBAD;
01169 }
01170
01171 #endif
01172
01173
01174
01175
01176
01177
01178
01179
01180
01181 bool
01182 ffetarget_hollerith (ffetargetHollerith *val, ffelexToken integer,
01183 mallocPool pool)
01184 {
01185 val->length = ffelex_token_length (integer);
01186 val->text = malloc_new_kp (pool, "ffetargetHollerith", val->length + 1);
01187 memcpy (val->text, ffelex_token_text (integer), val->length);
01188 val->text[val->length] = '\0';
01189
01190 return TRUE;
01191 }
01192
01193
01194
01195
01196
01197 void
01198 ffetarget_integer_bad_magical (ffelexToken t)
01199 {
01200 ffebad_start (FFEBAD_BAD_MAGICAL);
01201 ffebad_here (0, ffelex_token_where_line (t), ffelex_token_where_column (t));
01202 ffebad_finish ();
01203 }
01204
01205
01206
01207
01208
01209 void
01210 ffetarget_integer_bad_magical_binary (ffelexToken integer,
01211 ffelexToken minus)
01212 {
01213 ffebad_start (FFEBAD_BAD_MAGICAL_BINARY);
01214 ffebad_here (0, ffelex_token_where_line (integer),
01215 ffelex_token_where_column (integer));
01216 ffebad_here (1, ffelex_token_where_line (minus),
01217 ffelex_token_where_column (minus));
01218 ffebad_finish ();
01219 }
01220
01221
01222
01223
01224
01225
01226 void
01227 ffetarget_integer_bad_magical_precedence (ffelexToken integer,
01228 ffelexToken uminus,
01229 ffelexToken higher_op)
01230 {
01231 ffebad_start (FFEBAD_BAD_MAGICAL_PRECEDENCE);
01232 ffebad_here (0, ffelex_token_where_line (integer),
01233 ffelex_token_where_column (integer));
01234 ffebad_here (1, ffelex_token_where_line (uminus),
01235 ffelex_token_where_column (uminus));
01236 ffebad_here (2, ffelex_token_where_line (higher_op),
01237 ffelex_token_where_column (higher_op));
01238 ffebad_finish ();
01239 }
01240
01241
01242
01243
01244
01245 void
01246 ffetarget_integer_bad_magical_precedence_binary (ffelexToken integer,
01247 ffelexToken minus,
01248 ffelexToken higher_op)
01249 {
01250 ffebad_start (FFEBAD_BAD_MAGICAL_PRECEDENCE_BINARY);
01251 ffebad_here (0, ffelex_token_where_line (integer),
01252 ffelex_token_where_column (integer));
01253 ffebad_here (1, ffelex_token_where_line (minus),
01254 ffelex_token_where_column (minus));
01255 ffebad_here (2, ffelex_token_where_line (higher_op),
01256 ffelex_token_where_column (higher_op));
01257 ffebad_finish ();
01258 }
01259
01260
01261
01262
01263
01264
01265
01266 #if FFETARGET_okINTEGER1
01267 bool
01268 ffetarget_integer1 (ffetargetInteger1 *val, ffelexToken integer)
01269 {
01270 ffetargetInteger1 x;
01271 char *p;
01272 char c;
01273
01274 assert (ffelex_token_type (integer) == FFELEX_typeNUMBER);
01275
01276 p = ffelex_token_text (integer);
01277 x = 0;
01278
01279
01280
01281 while (((c = *p) != '\0') && (c == '0'))
01282 ++p;
01283
01284
01285
01286 while (c != '\0')
01287 {
01288 if ((x == FFETARGET_integerALMOST_BIG_MAGICAL)
01289 && (c == '0' + FFETARGET_integerFINISH_BIG_MAGICAL)
01290 && (*(p + 1) == '\0'))
01291 {
01292 *val = (ffetargetInteger1) FFETARGET_integerBIG_MAGICAL;
01293 return TRUE;
01294 }
01295 else if (x == FFETARGET_integerALMOST_BIG_MAGICAL)
01296 {
01297 if ((c > '0' + FFETARGET_integerFINISH_BIG_MAGICAL)
01298 || (*(p + 1) != '\0'))
01299 {
01300 ffebad_start (FFEBAD_INTEGER_TOO_LARGE);
01301 ffebad_here (0, ffelex_token_where_line (integer),
01302 ffelex_token_where_column (integer));
01303 ffebad_finish ();
01304 *val = 0;
01305 return FALSE;
01306 }
01307 }
01308 else if (x > FFETARGET_integerALMOST_BIG_MAGICAL)
01309 {
01310 ffebad_start (FFEBAD_INTEGER_TOO_LARGE);
01311 ffebad_here (0, ffelex_token_where_line (integer),
01312 ffelex_token_where_column (integer));
01313 ffebad_finish ();
01314 *val = 0;
01315 return FALSE;
01316 }
01317 x = x * 10 + c - '0';
01318 c = *(++p);
01319 };
01320
01321 *val = x;
01322 return TRUE;
01323 }
01324
01325 #endif
01326
01327
01328
01329
01330
01331
01332
01333
01334 bool
01335 ffetarget_integerbinary (ffetargetIntegerDefault *val, ffelexToken integer)
01336 {
01337 ffetargetIntegerDefault x;
01338 char *p;
01339 char c;
01340 bool bad_digit;
01341
01342 assert ((ffelex_token_type (integer) == FFELEX_typeNAME)
01343 || (ffelex_token_type (integer) == FFELEX_typeNUMBER));
01344
01345 p = ffelex_token_text (integer);
01346 x = 0;
01347
01348
01349
01350 while (((c = *p) != '\0') && (c == '0'))
01351 ++p;
01352
01353
01354
01355 bad_digit = FALSE;
01356 while (c != '\0')
01357 {
01358 if ((c >= '0') && (c <= '1'))
01359 c -= '0';
01360 else
01361 {
01362 bad_digit = TRUE;
01363 c = 0;
01364 }
01365
01366 #if 0
01367
01368 if ((x == FFETARGET_integerALMOST_BIG_OVERFLOW_BINARY)
01369 && (c == FFETARGET_integerFINISH_BIG_OVERFLOW_BINARY)
01370 && (*(p + 1) == '\0'))
01371 {
01372 *val = FFETARGET_integerBIG_OVERFLOW_BINARY;
01373 return TRUE;
01374 }
01375 else
01376 #endif
01377 #if FFETARGET_integerFINISH_BIG_OVERFLOW_BINARY == 0
01378 if ((x & FFETARGET_integerALMOST_BIG_OVERFLOW_BINARY) != 0)
01379 #else
01380 if (x == FFETARGET_integerALMOST_BIG_OVERFLOW_BINARY)
01381 {
01382 if ((c > FFETARGET_integerFINISH_BIG_OVERFLOW_BINARY)
01383 || (*(p + 1) != '\0'))
01384 {
01385 ffebad_start (FFEBAD_INTEGER_TOO_LARGE);
01386 ffebad_here (0, ffelex_token_where_line (integer),
01387 ffelex_token_where_column (integer));
01388 ffebad_finish ();
01389 *val = 0;
01390 return FALSE;
01391 }
01392 }
01393 else if (x > FFETARGET_integerALMOST_BIG_OVERFLOW_BINARY)
01394 #endif
01395 {
01396 ffebad_start (FFEBAD_INTEGER_TOO_LARGE);
01397 ffebad_here (0, ffelex_token_where_line (integer),
01398 ffelex_token_where_column (integer));
01399 ffebad_finish ();
01400 *val = 0;
01401 return FALSE;
01402 }
01403 x = (x << 1) + c;
01404 c = *(++p);
01405 };
01406
01407 if (bad_digit)
01408 {
01409 ffebad_start (FFEBAD_INVALID_BINARY_DIGIT);
01410 ffebad_here (0, ffelex_token_where_line (integer),
01411 ffelex_token_where_column (integer));
01412 ffebad_finish ();
01413 }
01414
01415 *val = x;
01416 return !bad_digit;
01417 }
01418
01419
01420
01421
01422
01423
01424
01425
01426
01427 bool
01428 ffetarget_integerhex (ffetargetIntegerDefault *val, ffelexToken integer)
01429 {
01430 ffetargetIntegerDefault x;
01431 char *p;
01432 char c;
01433 bool bad_digit;
01434
01435 assert ((ffelex_token_type (integer) == FFELEX_typeNAME)
01436 || (ffelex_token_type (integer) == FFELEX_typeNUMBER));
01437
01438 p = ffelex_token_text (integer);
01439 x = 0;
01440
01441
01442
01443 while (((c = *p) != '\0') && (c == '0'))
01444 ++p;
01445
01446
01447
01448 bad_digit = FALSE;
01449 while (c != '\0')
01450 {
01451 if (hex_p (c))
01452 c = hex_value (c);
01453 else
01454 {
01455 bad_digit = TRUE;
01456 c = 0;
01457 }
01458
01459 #if 0
01460
01461 if ((x == FFETARGET_integerALMOST_BIG_OVERFLOW_HEX)
01462 && (c == FFETARGET_integerFINISH_BIG_OVERFLOW_HEX)
01463 && (*(p + 1) == '\0'))
01464 {
01465 *val = FFETARGET_integerBIG_OVERFLOW_HEX;
01466 return TRUE;
01467 }
01468 else
01469 #endif
01470 #if FFETARGET_integerFINISH_BIG_OVERFLOW_HEX == 0
01471 if (x >= FFETARGET_integerALMOST_BIG_OVERFLOW_HEX)
01472 #else
01473 if (x == FFETARGET_integerALMOST_BIG_OVERFLOW_HEX)
01474 {
01475 if ((c > FFETARGET_integerFINISH_BIG_OVERFLOW_HEX)
01476 || (*(p + 1) != '\0'))
01477 {
01478 ffebad_start (FFEBAD_INTEGER_TOO_LARGE);
01479 ffebad_here (0, ffelex_token_where_line (integer),
01480 ffelex_token_where_column (integer));
01481 ffebad_finish ();
01482 *val = 0;
01483 return FALSE;
01484 }
01485 }
01486 else if (x > FFETARGET_integerALMOST_BIG_OVERFLOW_HEX)
01487 #endif
01488 {
01489 ffebad_start (FFEBAD_INTEGER_TOO_LARGE);
01490 ffebad_here (0, ffelex_token_where_line (integer),
01491 ffelex_token_where_column (integer));
01492 ffebad_finish ();
01493 *val = 0;
01494 return FALSE;
01495 }
01496 x = (x << 4) + c;
01497 c = *(++p);
01498 };
01499
01500 if (bad_digit)
01501 {
01502 ffebad_start (FFEBAD_INVALID_HEX_DIGIT);
01503 ffebad_here (0, ffelex_token_where_line (integer),
01504 ffelex_token_where_column (integer));
01505 ffebad_finish ();
01506 }
01507
01508 *val = x;
01509 return !bad_digit;
01510 }
01511
01512
01513
01514
01515
01516
01517
01518
01519
01520 bool
01521 ffetarget_integeroctal (ffetargetIntegerDefault *val, ffelexToken integer)
01522 {
01523 ffetargetIntegerDefault x;
01524 char *p;
01525 char c;
01526 bool bad_digit;
01527
01528 assert ((ffelex_token_type (integer) == FFELEX_typeNAME)
01529 || (ffelex_token_type (integer) == FFELEX_typeNUMBER));
01530
01531 p = ffelex_token_text (integer);
01532 x = 0;
01533
01534
01535
01536 while (((c = *p) != '\0') && (c == '0'))
01537 ++p;
01538
01539
01540
01541 bad_digit = FALSE;
01542 while (c != '\0')
01543 {
01544 if ((c >= '0') && (c <= '7'))
01545 c -= '0';
01546 else
01547 {
01548 bad_digit = TRUE;
01549 c = 0;
01550 }
01551
01552 #if 0
01553
01554 if ((x == FFETARGET_integerALMOST_BIG_OVERFLOW_OCTAL)
01555 && (c == FFETARGET_integerFINISH_BIG_OVERFLOW_OCTAL)
01556 && (*(p + 1) == '\0'))
01557 {
01558 *val = FFETARGET_integerBIG_OVERFLOW_OCTAL;
01559 return TRUE;
01560 }
01561 else
01562 #endif
01563 #if FFETARGET_integerFINISH_BIG_OVERFLOW_OCTAL == 0
01564 if (x >= FFETARGET_integerALMOST_BIG_OVERFLOW_OCTAL)
01565 #else
01566 if (x == FFETARGET_integerALMOST_BIG_OVERFLOW_OCTAL)
01567 {
01568 if ((c > FFETARGET_integerFINISH_BIG_OVERFLOW_OCTAL)
01569 || (*(p + 1) != '\0'))
01570 {
01571 ffebad_start (FFEBAD_INTEGER_TOO_LARGE);
01572 ffebad_here (0, ffelex_token_where_line (integer),
01573 ffelex_token_where_column (integer));
01574 ffebad_finish ();
01575 *val = 0;
01576 return FALSE;
01577 }
01578 }
01579 else if (x > FFETARGET_integerALMOST_BIG_OVERFLOW_OCTAL)
01580 #endif
01581 {
01582 ffebad_start (FFEBAD_INTEGER_TOO_LARGE);
01583 ffebad_here (0, ffelex_token_where_line (integer),
01584 ffelex_token_where_column (integer));
01585 ffebad_finish ();
01586 *val = 0;
01587 return FALSE;
01588 }
01589 x = (x << 3) + c;
01590 c = *(++p);
01591 };
01592
01593 if (bad_digit)
01594 {
01595 ffebad_start (FFEBAD_INVALID_OCTAL_DIGIT);
01596 ffebad_here (0, ffelex_token_where_line (integer),
01597 ffelex_token_where_column (integer));
01598 ffebad_finish ();
01599 }
01600
01601 *val = x;
01602 return !bad_digit;
01603 }
01604
01605
01606
01607
01608
01609 #if FFETARGET_okCOMPLEX1
01610 ffebad
01611 ffetarget_multiply_complex1 (ffetargetComplex1 *res, ffetargetComplex1 l,
01612 ffetargetComplex1 r)
01613 {
01614 ffebad bad;
01615 ffetargetReal1 tmp1, tmp2;
01616
01617 bad = ffetarget_multiply_real1 (&tmp1, l.real, r.real);
01618 if (bad != FFEBAD)
01619 return bad;
01620 bad = ffetarget_multiply_real1 (&tmp2, l.imaginary, r.imaginary);
01621 if (bad != FFEBAD)
01622 return bad;
01623 bad = ffetarget_subtract_real1 (&res->real, tmp1, tmp2);
01624 if (bad != FFEBAD)
01625 return bad;
01626 bad = ffetarget_multiply_real1 (&tmp1, l.imaginary, r.real);
01627 if (bad != FFEBAD)
01628 return bad;
01629 bad = ffetarget_multiply_real1 (&tmp2, l.real, r.imaginary);
01630 if (bad != FFEBAD)
01631 return bad;
01632 bad = ffetarget_add_real1 (&res->imaginary, tmp1, tmp2);
01633
01634 return bad;
01635 }
01636
01637 #endif
01638
01639
01640
01641
01642 #if FFETARGET_okCOMPLEX2
01643 ffebad
01644 ffetarget_multiply_complex2 (ffetargetComplex2 *res, ffetargetComplex2 l,
01645 ffetargetComplex2 r)
01646 {
01647 ffebad bad;
01648 ffetargetReal2 tmp1, tmp2;
01649
01650 bad = ffetarget_multiply_real2 (&tmp1, l.real, r.real);
01651 if (bad != FFEBAD)
01652 return bad;
01653 bad = ffetarget_multiply_real2 (&tmp2, l.imaginary, r.imaginary);
01654 if (bad != FFEBAD)
01655 return bad;
01656 bad = ffetarget_subtract_real2 (&res->real, tmp1, tmp2);
01657 if (bad != FFEBAD)
01658 return bad;
01659 bad = ffetarget_multiply_real2 (&tmp1, l.imaginary, r.real);
01660 if (bad != FFEBAD)
01661 return bad;
01662 bad = ffetarget_multiply_real2 (&tmp2, l.real, r.imaginary);
01663 if (bad != FFEBAD)
01664 return bad;
01665 bad = ffetarget_add_real2 (&res->imaginary, tmp1, tmp2);
01666
01667 return bad;
01668 }
01669
01670 #endif
01671
01672
01673
01674
01675 ffebad
01676 ffetarget_power_complexdefault_integerdefault (ffetargetComplexDefault *res,
01677 ffetargetComplexDefault l,
01678 ffetargetIntegerDefault r)
01679 {
01680 ffebad bad;
01681 ffetargetRealDefault tmp;
01682 ffetargetRealDefault tmp1;
01683 ffetargetRealDefault tmp2;
01684 ffetargetRealDefault two;
01685
01686 if (ffetarget_iszero_real1 (l.real)
01687 && ffetarget_iszero_real1 (l.imaginary))
01688 {
01689 ffetarget_real1_zero (&res->real);
01690 ffetarget_real1_zero (&res->imaginary);
01691 return FFEBAD;
01692 }
01693
01694 if (r == 0)
01695 {
01696 ffetarget_real1_one (&res->real);
01697 ffetarget_real1_zero (&res->imaginary);
01698 return FFEBAD;
01699 }
01700
01701 if (r < 0)
01702 {
01703 r = -r;
01704 bad = ffetarget_multiply_real1 (&tmp1, l.real, l.real);
01705 if (bad != FFEBAD)
01706 return bad;
01707 bad = ffetarget_multiply_real1 (&tmp2, l.imaginary, l.imaginary);
01708 if (bad != FFEBAD)
01709 return bad;
01710 bad = ffetarget_add_real1 (&tmp, tmp1, tmp2);
01711 if (bad != FFEBAD)
01712 return bad;
01713 bad = ffetarget_divide_real1 (&l.real, l.real, tmp);
01714 if (bad != FFEBAD)
01715 return bad;
01716 bad = ffetarget_divide_real1 (&l.imaginary, l.imaginary, tmp);
01717 if (bad != FFEBAD)
01718 return bad;
01719 bad = ffetarget_uminus_real1 (&l.imaginary, l.imaginary);
01720 if (bad != FFEBAD)
01721 return bad;
01722 }
01723
01724 ffetarget_real1_two (&two);
01725
01726 while ((r & 1) == 0)
01727 {
01728 bad = ffetarget_multiply_real1 (&tmp1, l.real, l.real);
01729 if (bad != FFEBAD)
01730 return bad;
01731 bad = ffetarget_multiply_real1 (&tmp2, l.imaginary, l.imaginary);
01732 if (bad != FFEBAD)
01733 return bad;
01734 bad = ffetarget_subtract_real1 (&tmp, tmp1, tmp2);
01735 if (bad != FFEBAD)
01736 return bad;
01737 bad = ffetarget_multiply_real1 (&l.imaginary, l.real, l.imaginary);
01738 if (bad != FFEBAD)
01739 return bad;
01740 bad = ffetarget_multiply_real1 (&l.imaginary, l.imaginary, two);
01741 if (bad != FFEBAD)
01742 return bad;
01743 l.real = tmp;
01744 r >>= 1;
01745 }
01746
01747 *res = l;
01748 r >>= 1;
01749
01750 while (r != 0)
01751 {
01752 bad = ffetarget_multiply_real1 (&tmp1, l.real, l.real);
01753 if (bad != FFEBAD)
01754 return bad;
01755 bad = ffetarget_multiply_real1 (&tmp2, l.imaginary, l.imaginary);
01756 if (bad != FFEBAD)
01757 return bad;
01758 bad = ffetarget_subtract_real1 (&tmp, tmp1, tmp2);
01759 if (bad != FFEBAD)
01760 return bad;
01761 bad = ffetarget_multiply_real1 (&l.imaginary, l.real, l.imaginary);
01762 if (bad != FFEBAD)
01763 return bad;
01764 bad = ffetarget_multiply_real1 (&l.imaginary, l.imaginary, two);
01765 if (bad != FFEBAD)
01766 return bad;
01767 l.real = tmp;
01768 if ((r & 1) == 1)
01769 {
01770 bad = ffetarget_multiply_real1 (&tmp1, res->real, l.real);
01771 if (bad != FFEBAD)
01772 return bad;
01773 bad = ffetarget_multiply_real1 (&tmp2, res->imaginary,
01774 l.imaginary);
01775 if (bad != FFEBAD)
01776 return bad;
01777 bad = ffetarget_subtract_real1 (&tmp, tmp1, tmp2);
01778 if (bad != FFEBAD)
01779 return bad;
01780 bad = ffetarget_multiply_real1 (&tmp1, res->imaginary, l.real);
01781 if (bad != FFEBAD)
01782 return bad;
01783 bad = ffetarget_multiply_real1 (&tmp2, res->real, l.imaginary);
01784 if (bad != FFEBAD)
01785 return bad;
01786 bad = ffetarget_add_real1 (&res->imaginary, tmp1, tmp2);
01787 if (bad != FFEBAD)
01788 return bad;
01789 res->real = tmp;
01790 }
01791 r >>= 1;
01792 }
01793
01794 return FFEBAD;
01795 }
01796
01797
01798
01799
01800
01801 #if FFETARGET_okCOMPLEXDOUBLE
01802 ffebad
01803 ffetarget_power_complexdouble_integerdefault (ffetargetComplexDouble *res,
01804 ffetargetComplexDouble l, ffetargetIntegerDefault r)
01805 {
01806 ffebad bad;
01807 ffetargetRealDouble tmp;
01808 ffetargetRealDouble tmp1;
01809 ffetargetRealDouble tmp2;
01810 ffetargetRealDouble two;
01811
01812 if (ffetarget_iszero_real2 (l.real)
01813 && ffetarget_iszero_real2 (l.imaginary))
01814 {
01815 ffetarget_real2_zero (&res->real);
01816 ffetarget_real2_zero (&res->imaginary);
01817 return FFEBAD;
01818 }
01819
01820 if (r == 0)
01821 {
01822 ffetarget_real2_one (&res->real);
01823 ffetarget_real2_zero (&res->imaginary);
01824 return FFEBAD;
01825 }
01826
01827 if (r < 0)
01828 {
01829 r = -r;
01830 bad = ffetarget_multiply_real2 (&tmp1, l.real, l.real);
01831 if (bad != FFEBAD)
01832 return bad;
01833 bad = ffetarget_multiply_real2 (&tmp2, l.imaginary, l.imaginary);
01834 if (bad != FFEBAD)
01835 return bad;
01836 bad = ffetarget_add_real2 (&tmp, tmp1, tmp2);
01837 if (bad != FFEBAD)
01838 return bad;
01839 bad = ffetarget_divide_real2 (&l.real, l.real, tmp);
01840 if (bad != FFEBAD)
01841 return bad;
01842 bad = ffetarget_divide_real2 (&l.imaginary, l.imaginary, tmp);
01843 if (bad != FFEBAD)
01844 return bad;
01845 bad = ffetarget_uminus_real2 (&l.imaginary, l.imaginary);
01846 if (bad != FFEBAD)
01847 return bad;
01848 }
01849
01850 ffetarget_real2_two (&two);
01851
01852 while ((r & 1) == 0)
01853 {
01854 bad = ffetarget_multiply_real2 (&tmp1, l.real, l.real);
01855 if (bad != FFEBAD)
01856 return bad;
01857 bad = ffetarget_multiply_real2 (&tmp2, l.imaginary, l.imaginary);
01858 if (bad != FFEBAD)
01859 return bad;
01860 bad = ffetarget_subtract_real2 (&tmp, tmp1, tmp2);
01861 if (bad != FFEBAD)
01862 return bad;
01863 bad = ffetarget_multiply_real2 (&l.imaginary, l.real, l.imaginary);
01864 if (bad != FFEBAD)
01865 return bad;
01866 bad = ffetarget_multiply_real2 (&l.imaginary, l.imaginary, two);
01867 if (bad != FFEBAD)
01868 return bad;
01869 l.real = tmp;
01870 r >>= 1;
01871 }
01872
01873 *res = l;
01874 r >>= 1;
01875
01876 while (r != 0)
01877 {
01878 bad = ffetarget_multiply_real2 (&tmp1, l.real, l.real);
01879 if (bad != FFEBAD)
01880 return bad;
01881 bad = ffetarget_multiply_real2 (&tmp2, l.imaginary, l.imaginary);
01882 if (bad != FFEBAD)
01883 return bad;
01884 bad = ffetarget_subtract_real2 (&tmp, tmp1, tmp2);
01885 if (bad != FFEBAD)
01886 return bad;
01887 bad = ffetarget_multiply_real2 (&l.imaginary, l.real, l.imaginary);
01888 if (bad != FFEBAD)
01889 return bad;
01890 bad = ffetarget_multiply_real2 (&l.imaginary, l.imaginary, two);
01891 if (bad != FFEBAD)
01892 return bad;
01893 l.real = tmp;
01894 if ((r & 1) == 1)
01895 {
01896 bad = ffetarget_multiply_real2 (&tmp1, res->real, l.real);
01897 if (bad != FFEBAD)
01898 return bad;
01899 bad = ffetarget_multiply_real2 (&tmp2, res->imaginary,
01900 l.imaginary);
01901 if (bad != FFEBAD)
01902 return bad;
01903 bad = ffetarget_subtract_real2 (&tmp, tmp1, tmp2);
01904 if (bad != FFEBAD)
01905 return bad;
01906 bad = ffetarget_multiply_real2 (&tmp1, res->imaginary, l.real);
01907 if (bad != FFEBAD)
01908 return bad;
01909 bad = ffetarget_multiply_real2 (&tmp2, res->real, l.imaginary);
01910 if (bad != FFEBAD)
01911 return bad;
01912 bad = ffetarget_add_real2 (&res->imaginary, tmp1, tmp2);
01913 if (bad != FFEBAD)
01914 return bad;
01915 res->real = tmp;
01916 }
01917 r >>= 1;
01918 }
01919
01920 return FFEBAD;
01921 }
01922
01923 #endif
01924
01925
01926
01927
01928 ffebad
01929 ffetarget_power_integerdefault_integerdefault (ffetargetIntegerDefault *res,
01930 ffetargetIntegerDefault l, ffetargetIntegerDefault r)
01931 {
01932 if (l == 0)
01933 {
01934 *res = 0;
01935 return FFEBAD;
01936 }
01937
01938 if (r == 0)
01939 {
01940 *res = 1;
01941 return FFEBAD;
01942 }
01943
01944 if (r < 0)
01945 {
01946 if (l == 1)
01947 *res = 1;
01948 else if (l == 0)
01949 *res = 1;
01950 else if (l == -1)
01951 *res = ((-r) & 1) == 0 ? 1 : -1;
01952 else
01953 *res = 0;
01954 return FFEBAD;
01955 }
01956
01957 while ((r & 1) == 0)
01958 {
01959 l *= l;
01960 r >>= 1;
01961 }
01962
01963 *res = l;
01964 r >>= 1;
01965
01966 while (r != 0)
01967 {
01968 l *= l;
01969 if ((r & 1) == 1)
01970 *res *= l;
01971 r >>= 1;
01972 }
01973
01974 return FFEBAD;
01975 }
01976
01977
01978
01979
01980
01981 ffebad
01982 ffetarget_power_realdefault_integerdefault (ffetargetRealDefault *res,
01983 ffetargetRealDefault l, ffetargetIntegerDefault r)
01984 {
01985 ffebad bad;
01986
01987 if (ffetarget_iszero_real1 (l))
01988 {
01989 ffetarget_real1_zero (res);
01990 return FFEBAD;
01991 }
01992
01993 if (r == 0)
01994 {
01995 ffetarget_real1_one (res);
01996 return FFEBAD;
01997 }
01998
01999 if (r < 0)
02000 {
02001 ffetargetRealDefault one;
02002
02003 ffetarget_real1_one (&one);
02004 r = -r;
02005 bad = ffetarget_divide_real1 (&l, one, l);
02006 if (bad != FFEBAD)
02007 return bad;
02008 }
02009
02010 while ((r & 1) == 0)
02011 {
02012 bad = ffetarget_multiply_real1 (&l, l, l);
02013 if (bad != FFEBAD)
02014 return bad;
02015 r >>= 1;
02016 }
02017
02018 *res = l;
02019 r >>= 1;
02020
02021 while (r != 0)
02022 {
02023 bad = ffetarget_multiply_real1 (&l, l, l);
02024 if (bad != FFEBAD)
02025 return bad;
02026 if ((r & 1) == 1)
02027 {
02028 bad = ffetarget_multiply_real1 (res, *res, l);
02029 if (bad != FFEBAD)
02030 return bad;
02031 }
02032 r >>= 1;
02033 }
02034
02035 return FFEBAD;
02036 }
02037
02038
02039
02040
02041
02042 ffebad
02043 ffetarget_power_realdouble_integerdefault (ffetargetRealDouble *res,
02044 ffetargetRealDouble l,
02045 ffetargetIntegerDefault r)
02046 {
02047 ffebad bad;
02048
02049 if (ffetarget_iszero_real2 (l))
02050 {
02051 ffetarget_real2_zero (res);
02052 return FFEBAD;
02053 }
02054
02055 if (r == 0)
02056 {
02057 ffetarget_real2_one (res);
02058 return FFEBAD;
02059 }
02060
02061 if (r < 0)
02062 {
02063 ffetargetRealDouble one;
02064
02065 ffetarget_real2_one (&one);
02066 r = -r;
02067 bad = ffetarget_divide_real2 (&l, one, l);
02068 if (bad != FFEBAD)
02069 return bad;
02070 }
02071
02072 while ((r & 1) == 0)
02073 {
02074 bad = ffetarget_multiply_real2 (&l, l, l);
02075 if (bad != FFEBAD)
02076 return bad;
02077 r >>= 1;
02078 }
02079
02080 *res = l;
02081 r >>= 1;
02082
02083 while (r != 0)
02084 {
02085 bad = ffetarget_multiply_real2 (&l, l, l);
02086 if (bad != FFEBAD)
02087 return bad;
02088 if ((r & 1) == 1)
02089 {
02090 bad = ffetarget_multiply_real2 (res, *res, l);
02091 if (bad != FFEBAD)
02092 return bad;
02093 }
02094 r >>= 1;
02095 }
02096
02097 return FFEBAD;
02098 }
02099
02100
02101
02102
02103
02104
02105 void
02106 ffetarget_print_binary (FILE *f, ffetargetTypeless value)
02107 {
02108 char *p;
02109 char digits[sizeof (value) * CHAR_BIT + 1];
02110
02111 if (f == NULL)
02112 f = dmpout;
02113
02114 p = &digits[ARRAY_SIZE (digits) - 1];
02115 *p = '\0';
02116 do
02117 {
02118 *--p = (value & 1) + '0';
02119 value >>= 1;
02120 } while (value == 0);
02121
02122 fputs (p, f);
02123 }
02124
02125
02126
02127
02128
02129
02130 void
02131 ffetarget_print_character1 (FILE *f, ffetargetCharacter1 value)
02132 {
02133 unsigned char *p;
02134 ffetargetCharacterSize i;
02135
02136 fputc ('\'', dmpout);
02137 for (i = 0, p = value.text; i < value.length; ++i, ++p)
02138 ffetarget_print_char_ (f, *p);
02139 fputc ('\'', dmpout);
02140 }
02141
02142
02143
02144
02145
02146
02147 void
02148 ffetarget_print_hollerith (FILE *f, ffetargetHollerith value)
02149 {
02150 unsigned char *p;
02151 ffetargetHollerithSize i;
02152
02153 fputc ('\'', dmpout);
02154 for (i = 0, p = value.text; i < value.length; ++i, ++p)
02155 ffetarget_print_char_ (f, *p);
02156 fputc ('\'', dmpout);
02157 }
02158
02159
02160
02161
02162
02163
02164 void
02165 ffetarget_print_octal (FILE *f, ffetargetTypeless value)
02166 {
02167 char *p;
02168 char digits[sizeof (value) * CHAR_BIT / 3 + 1];
02169
02170 if (f == NULL)
02171 f = dmpout;
02172
02173 p = &digits[ARRAY_SIZE (digits) - 3];
02174 *p = '\0';
02175 do
02176 {
02177 *--p = (value & 3) + '0';
02178 value >>= 3;
02179 } while (value == 0);
02180
02181 fputs (p, f);
02182 }
02183
02184
02185
02186
02187
02188
02189 void
02190 ffetarget_print_hex (FILE *f, ffetargetTypeless value)
02191 {
02192 char *p;
02193 char digits[sizeof (value) * CHAR_BIT / 4 + 1];
02194 static char hexdigits[16] = "0123456789ABCDEF";
02195
02196 if (f == NULL)
02197 f = dmpout;
02198
02199 p = &digits[ARRAY_SIZE (digits) - 3];
02200 *p = '\0';
02201 do
02202 {
02203 *--p = hexdigits[value & 4];
02204 value >>= 4;
02205 } while (value == 0);
02206
02207 fputs (p, f);
02208 }
02209
02210
02211
02212
02213
02214
02215
02216
02217
02218
02219
02220 #if FFETARGET_okREAL1
02221 bool
02222 ffetarget_real1 (ffetargetReal1 *value, ffelexToken integer,
02223 ffelexToken decimal, ffelexToken fraction,
02224 ffelexToken exponent, ffelexToken exponent_sign,
02225 ffelexToken exponent_digits)
02226 {
02227 size_t sz = 1;
02228 char *ptr = &ffetarget_string_[0];
02229 char *p = ptr;
02230 char *q;
02231
02232 #define dotok(x) if (x != NULL) ++sz;
02233 #define dotoktxt(x) if (x != NULL) sz += ffelex_token_length(x)
02234
02235 dotoktxt (integer);
02236 dotok (decimal);
02237 dotoktxt (fraction);
02238 dotoktxt (exponent);
02239 dotok (exponent_sign);
02240 dotoktxt (exponent_digits);
02241
02242 #undef dotok
02243 #undef dotoktxt
02244
02245 if (sz > ARRAY_SIZE (ffetarget_string_))
02246 p = ptr = (char *) malloc_new_ks (malloc_pool_image (), "ffetarget_real1",
02247 sz);
02248
02249 #define dotoktxt(x) if (x != NULL) \
02250 { \
02251 for (q = ffelex_token_text(x); *q != '\0'; ++q) \
02252 *p++ = *q; \
02253 }
02254
02255 dotoktxt (integer);
02256
02257 if (decimal != NULL)
02258 *p++ = '.';
02259
02260 dotoktxt (fraction);
02261 dotoktxt (exponent);
02262
02263 if (exponent_sign != NULL)
02264 {
02265 if (ffelex_token_type (exponent_sign) == FFELEX_typePLUS)
02266 *p++ = '+';
02267 else
02268 {
02269 assert (ffelex_token_type (exponent_sign) == FFELEX_typeMINUS);
02270 *p++ = '-';
02271 }
02272 }
02273
02274 dotoktxt (exponent_digits);
02275
02276 #undef dotoktxt
02277
02278 *p = '\0';
02279
02280 ffetarget_make_real1 (value,
02281 FFETARGET_ATOF_ (ptr,
02282 SFmode));
02283
02284 if (sz > ARRAY_SIZE (ffetarget_string_))
02285 malloc_kill_ks (malloc_pool_image (), ptr, sz);
02286
02287 return TRUE;
02288 }
02289
02290 #endif
02291
02292
02293
02294
02295
02296
02297
02298
02299
02300
02301 #if FFETARGET_okREAL2
02302 bool
02303 ffetarget_real2 (ffetargetReal2 *value, ffelexToken integer,
02304 ffelexToken decimal, ffelexToken fraction,
02305 ffelexToken exponent, ffelexToken exponent_sign,
02306 ffelexToken exponent_digits)
02307 {
02308 size_t sz = 1;
02309 char *ptr = &ffetarget_string_[0];
02310 char *p = ptr;
02311 char *q;
02312
02313 #define dotok(x) if (x != NULL) ++sz;
02314 #define dotoktxt(x) if (x != NULL) sz += ffelex_token_length(x)
02315
02316 dotoktxt (integer);
02317 dotok (decimal);
02318 dotoktxt (fraction);
02319 dotoktxt (exponent);
02320 dotok (exponent_sign);
02321 dotoktxt (exponent_digits);
02322
02323 #undef dotok
02324 #undef dotoktxt
02325
02326 if (sz > ARRAY_SIZE (ffetarget_string_))
02327 p = ptr = (char *) malloc_new_ks (malloc_pool_image (), "ffetarget_real1", sz);
02328
02329 #define dotoktxt(x) if (x != NULL) \
02330 { \
02331 for (q = ffelex_token_text(x); *q != '\0'; ++q) \
02332 *p++ = *q; \
02333 }
02334 #define dotoktxtexp(x) if (x != NULL) \
02335 { \
02336 *p++ = 'E'; \
02337 for (q = ffelex_token_text(x) + 1; *q != '\0'; ++q) \
02338 *p++ = *q; \
02339 }
02340
02341 dotoktxt (integer);
02342
02343 if (decimal != NULL)
02344 *p++ = '.';
02345
02346 dotoktxt (fraction);
02347 dotoktxtexp (exponent);
02348
02349 if (exponent_sign != NULL)
02350 {
02351 if (ffelex_token_type (exponent_sign) == FFELEX_typePLUS)
02352 *p++ = '+';
02353 else
02354 {
02355 assert (ffelex_token_type (exponent_sign) == FFELEX_typeMINUS);
02356 *p++ = '-';
02357 }
02358 }
02359
02360 dotoktxt (exponent_digits);
02361
02362 #undef dotoktxt
02363
02364 *p = '\0';
02365
02366 ffetarget_make_real2 (value,
02367 FFETARGET_ATOF_ (ptr,
02368 DFmode));
02369
02370 if (sz > ARRAY_SIZE (ffetarget_string_))
02371 malloc_kill_ks (malloc_pool_image (), ptr, sz);
02372
02373 return TRUE;
02374 }
02375
02376 #endif
02377 bool
02378 ffetarget_typeless_binary (ffetargetTypeless *xvalue, ffelexToken token)
02379 {
02380 char *p;
02381 char c;
02382 ffetargetTypeless value = 0;
02383 ffetargetTypeless new_value = 0;
02384 bool bad_digit = FALSE;
02385 bool overflow = FALSE;
02386
02387 p = ffelex_token_text (token);
02388
02389 for (c = *p; c != '\0'; c = *++p)
02390 {
02391 new_value <<= 1;
02392 if ((new_value >> 1) != value)
02393 overflow = TRUE;
02394 if (ISDIGIT (c))
02395 new_value += c - '0';
02396 else
02397 bad_digit = TRUE;
02398 value = new_value;
02399 }
02400
02401 if (bad_digit)
02402 {
02403 ffebad_start (FFEBAD_INVALID_TYPELESS_BINARY_DIGIT);
02404 ffebad_here (0, ffelex_token_where_line (token),
02405 ffelex_token_where_column (token));
02406 ffebad_finish ();
02407 }
02408 else if (overflow)
02409 {
02410 ffebad_start (FFEBAD_TYPELESS_OVERFLOW);
02411 ffebad_here (0, ffelex_token_where_line (token),
02412 ffelex_token_where_column (token));
02413 ffebad_finish ();
02414 }
02415
02416 *xvalue = value;
02417
02418 return !bad_digit && !overflow;
02419 }
02420
02421 bool
02422 ffetarget_typeless_octal (ffetargetTypeless *xvalue, ffelexToken token)
02423 {
02424 char *p;
02425 char c;
02426 ffetargetTypeless value = 0;
02427 ffetargetTypeless new_value = 0;
02428 bool bad_digit = FALSE;
02429 bool overflow = FALSE;
02430
02431 p = ffelex_token_text (token);
02432
02433 for (c = *p; c != '\0'; c = *++p)
02434 {
02435 new_value <<= 3;
02436 if ((new_value >> 3) != value)
02437 overflow = TRUE;
02438 if (ISDIGIT (c))
02439 new_value += c - '0';
02440 else
02441 bad_digit = TRUE;
02442 value = new_value;
02443 }
02444
02445 if (bad_digit)
02446 {
02447 ffebad_start (FFEBAD_INVALID_TYPELESS_OCTAL_DIGIT);
02448 ffebad_here (0, ffelex_token_where_line (token),
02449 ffelex_token_where_column (token));
02450 ffebad_finish ();
02451 }
02452 else if (overflow)
02453 {
02454 ffebad_start (FFEBAD_TYPELESS_OVERFLOW);
02455 ffebad_here (0, ffelex_token_where_line (token),
02456 ffelex_token_where_column (token));
02457 ffebad_finish ();
02458 }
02459
02460 *xvalue = value;
02461
02462 return !bad_digit && !overflow;
02463 }
02464
02465 bool
02466 ffetarget_typeless_hex (ffetargetTypeless *xvalue, ffelexToken token)
02467 {
02468 char *p;
02469 char c;
02470 ffetargetTypeless value = 0;
02471 ffetargetTypeless new_value = 0;
02472 bool bad_digit = FALSE;
02473 bool overflow = FALSE;
02474
02475 p = ffelex_token_text (token);
02476
02477 for (c = *p; c != '\0'; c = *++p)
02478 {
02479 new_value <<= 4;
02480 if ((new_value >> 4) != value)
02481 overflow = TRUE;
02482 if (hex_p (c))
02483 new_value += hex_value (c);
02484 else
02485 bad_digit = TRUE;
02486 value = new_value;
02487 }
02488
02489 if (bad_digit)
02490 {
02491 ffebad_start (FFEBAD_INVALID_TYPELESS_HEX_DIGIT);
02492 ffebad_here (0, ffelex_token_where_line (token),
02493 ffelex_token_where_column (token));
02494 ffebad_finish ();
02495 }
02496 else if (overflow)
02497 {
02498 ffebad_start (FFEBAD_TYPELESS_OVERFLOW);
02499 ffebad_here (0, ffelex_token_where_line (token),
02500 ffelex_token_where_column (token));
02501 ffebad_finish ();
02502 }
02503
02504 *xvalue = value;
02505
02506 return !bad_digit && !overflow;
02507 }
02508
02509 void
02510 ffetarget_verify_character1 (mallocPool pool, ffetargetCharacter1 val)
02511 {
02512 if (val.length != 0)
02513 malloc_verify_kp (pool, val.text, val.length);
02514 }
02515
02516
02517
02518
02519
02520 void *
02521 ffetarget_memcpy_ (void *dst, void *src, size_t len)
02522 {
02523 #ifdef CROSS_COMPILE
02524
02525
02526
02527 int host_words_big_endian =
02528 #ifndef HOST_WORDS_BIG_ENDIAN
02529 0
02530 #else
02531 HOST_WORDS_BIG_ENDIAN
02532 #endif
02533 ;
02534
02535
02536
02537
02538
02539
02540
02541
02542
02543
02544 if (!WORDS_BIG_ENDIAN != !host_words_big_endian
02545 || !BYTES_BIG_ENDIAN != !host_words_big_endian)
02546 sorry ("data initializer on host with different endianness");
02547
02548 #endif
02549
02550 return (void *) memcpy (dst, src, len);
02551 }
02552
02553
02554
02555
02556
02557
02558
02559 int
02560 ffetarget_num_digits_ (ffelexToken token)
02561 {
02562 int i;
02563 char *c;
02564
02565 switch (ffelex_token_type (token))
02566 {
02567 case FFELEX_typeNAME:
02568 case FFELEX_typeNUMBER:
02569 return ffelex_token_length (token);
02570
02571 case FFELEX_typeCHARACTER:
02572 i = 0;
02573 for (c = ffelex_token_text (token); *c != '\0'; ++c)
02574 {
02575 if (*c != ' ')
02576 ++i;
02577 }
02578 return i;
02579
02580 default:
02581 assert ("weird token" == NULL);
02582 return 1;
02583 }
02584 }