Go to the documentation of this file.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 #pragma ident "@(#) libf/fio/wrfmt.c 92.6 06/21/99 10:37:55"
00039
00040 #include <memory.h>
00041 #include <stdlib.h>
00042 #include <string.h>
00043 #include <fortran.h>
00044 #include <cray/fmtconv.h>
00045 #include <cray/format.h>
00046 #include <cray/nassert.h>
00047 #ifdef _CRAYT3D
00048 #include <cray/mppsdd.h>
00049 #define MAXSH 512
00050 #else
00051 #define MAXSH 1
00052 #endif
00053 #include "fio.h"
00054 #include "fmt.h"
00055 #include "f90io.h"
00056 #include "lio.h"
00057
00058 extern const oc_func *_oconvtab[LAST_DATA_ED + 1];
00059 extern const short _odedtab[DVTYPE_NTYPES];
00060 extern short _o_sup_flg_tab[DVTYPE_NTYPES];
00061 extern long _o_sup_val_tab[DVTYPE_NTYPES];
00062
00063 #undef BLANK
00064 #define BLANK ((long) ' ')
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074 int
00075 _wrfmt(
00076 FIOSPTR css,
00077 unit *cup,
00078 void *dptr,
00079 type_packet *tip,
00080 int _Unused
00081 )
00082 {
00083 register short cswitch;
00084 register short fmtop;
00085 register short part;
00086 register short supflg;
00087 register ftype_t type;
00088 register int32 delta;
00089 register int32 field;
00090 register int32 i;
00091 register int32 kount;
00092 register int32 length;
00093 register int32 repcnt;
00094 int cinc[2];
00095 register int stat;
00096 register int stride;
00097 register char *cptr;
00098 register char *ctmp;
00099 long digits;
00100 long exp;
00101 long mode;
00102 long width;
00103 register long count;
00104 register long dfmode;
00105 fmt_type pfmt;
00106 #ifdef _CRAYT3D
00107 register short shared;
00108 register int elwords;
00109 register int offset;
00110 register int32 tcount;
00111 long shrd[MAXSH];
00112 #endif
00113
00114 const oc_func *ngcf;
00115
00116
00117
00118 assert (cup != NULL);
00119 assert (tip != NULL);
00120
00121 type = tip->type90;
00122 count = tip->count;
00123
00124 cswitch = 0;
00125 stat = 0;
00126 part = 1;
00127
00128 pfmt = *css->u.fmt.u.fe.pfcp;
00129 repcnt = *css->u.fmt.u.fe.pftocs;
00130 length = tip->elsize;
00131 stride = tip->stride * length;
00132 cinc[1] = stride;
00133 supflg = _o_sup_flg_tab[type] && (length == sizeof(long));
00134
00135
00136
00137 if (type == DVTYPE_COMPLEX) {
00138 length = length / 2;
00139 cinc[0] = length;
00140 cinc[1] = stride - length;
00141 cswitch = 1;
00142 part = 0;
00143 }
00144
00145 dfmode = ((cup->uft90 == 0) ? MODE77 : 0) |
00146 ((css->u.fmt.cplus == 1) ? MODESN : 0);
00147
00148 #ifdef _CRAYT3D
00149 if (_issddptr(dptr)) {
00150 offset = 0;
00151 elwords = tip->elsize / sizeof(long);
00152 shared = 1;
00153 stride = tip->elsize;
00154 tcount = count;
00155 }
00156 else
00157 shared = 0;
00158
00159 do {
00160 if (shared) {
00161
00162
00163 count = MIN(MAXSH/elwords, (tcount - offset));
00164 cptr = (char *) shrd;
00165
00166 (void) _cpyfrmsdd(dptr, shrd, count, elwords, tip->stride, offset);
00167 offset = offset + count;
00168 }
00169 else
00170 #endif
00171 {
00172 cptr = (char *) dptr;
00173 }
00174
00175 do {
00176
00177 fmtop = pfmt.op_code;
00178 width = pfmt.field_width;
00179 digits = pfmt.digits_field;
00180 exp = pfmt.exponent;
00181
00182
00183
00184 if (fmtop > LAST_OP || fmtop < FIRST_DATA_ED) {
00185 stat = FEINTIPF;
00186 goto done;
00187 }
00188
00189 if (fmtop <= LAST_DATA_ED || fmtop == STRING_ED) {
00190
00191 if (fmtop == STRING_ED)
00192
00193 kount = repcnt;
00194
00195 else {
00196
00197
00198
00199
00200
00201
00202
00203 if (count == 0)
00204 goto done;
00205
00206
00207
00208
00209
00210
00211
00212 if (INVALID_WTYPE(fmtop, type)) {
00213
00214 stat = FEWRTYPE;
00215 goto done;
00216 }
00217
00218 if (fmtop == G_ED) {
00219
00220 fmtop = _odedtab[type];
00221
00222 if (type != DVTYPE_REAL &&
00223 type != DVTYPE_COMPLEX)
00224 digits = 1;
00225 }
00226
00227
00228
00229
00230
00231
00232 if (type == DVTYPE_ASCII)
00233 mode = 0;
00234 else {
00235 mode = (long) _wr_ilchk[fmtop-1][length-1];
00236
00237 if (mode == INVALID_INTLEN) {
00238
00239 stat = FEWRTYPE;
00240 goto done;
00241 }
00242 }
00243
00244
00245
00246
00247
00248
00249 if ((type == DVTYPE_REAL ||
00250 type == DVTYPE_COMPLEX) &&
00251 cup->ufnegzero != 0)
00252 mode = mode | MODEMSN;
00253
00254 mode = mode | dfmode;
00255
00256
00257
00258
00259
00260 if (width == 0) {
00261 switch (fmtop) {
00262
00263
00264
00265
00266
00267
00268 case A_ED:
00269 case R_ED:
00270 width = length;
00271 break;
00272
00273
00274
00275
00276
00277
00278
00279
00280 case B_ED:
00281 case I_ED:
00282 case O_ED:
00283 case Z_ED:
00284 width = _rw_mxdgt[fmtop-1][length-1];
00285
00286
00287 if (width == 127)
00288 width = 128;
00289
00290 if (pfmt.default_digits)
00291 digits = 1;
00292 else if (width < digits)
00293 width = digits;
00294
00295
00296
00297 width = width + 1;
00298
00299 if (fmtop == I_ED)
00300 width = width + 1;
00301
00302
00303
00304
00305
00306
00307
00308
00309
00310
00311
00312
00313 if (digits == 0) {
00314 register int64 datum;
00315
00316 switch (length) {
00317
00318 case 8:
00319 datum = *(int64 *) cptr;
00320 break;
00321
00322 #ifndef _CRAY1
00323 case 4:
00324 datum = *(int32 *) cptr;
00325 break;
00326 #endif
00327
00328 #if defined(__mips) || defined(_SOLARIS) || defined(_LITTLE_ENDIAN)
00329 case 2:
00330 datum = *(short *) cptr;
00331 break;
00332
00333 case 1:
00334 datum = *cptr;
00335 break;
00336 #endif
00337
00338 }
00339
00340 if (datum == 0)
00341 width = 1;
00342 }
00343 break;
00344
00345
00346
00347
00348
00349
00350
00351
00352
00353
00354
00355
00356 case D_ED:
00357 case E_ED:
00358 case EN_ED:
00359 case ES_ED:
00360 case F_ED:
00361 case G_ED:
00362 if (pfmt.default_digits)
00363 digits = _rw_mxdgt[fmtop-1][length-1];
00364
00365 if (exp == 0) {
00366 if (length == 16)
00367 exp = DEXP16;
00368 #ifdef _F_REAL4
00369 else if (length == 4)
00370 exp = DEXP4;
00371 #endif
00372 else
00373 exp = DEXP8;
00374 }
00375
00376 width = digits + exp + 6;
00377 break;
00378
00379
00380
00381
00382
00383
00384
00385 case L_ED:
00386 width = _rw_mxdgt[fmtop-1][length-1];
00387 break;
00388
00389
00390
00391
00392
00393 case Q_ED:
00394 width = 0;
00395 break;
00396
00397
00398
00399
00400 default:
00401 width = -1;
00402 break;
00403 }
00404
00405
00406
00407
00408 if (width < 0) {
00409 stat = FEWRTYPE;
00410 goto done;
00411 }
00412 }
00413
00414
00415
00416
00417
00418
00419
00420 kount = MIN(repcnt,
00421 ((count << cswitch) - (part & cswitch)));
00422 }
00423
00424 field = width * kount;
00425
00426
00427
00428
00429
00430
00431
00432
00433
00434 if (cup->ulinecnt > cup->ulinemax) {
00435 register short j, k;
00436
00437 if (cup->ulinecnt > cup->urecsize) {
00438 stat = FEWRLONG;
00439 goto done;
00440 }
00441
00442 k = cup->ulinecnt;
00443
00444
00445
00446 for (j = cup->ulinemax; j < k; j++)
00447 cup->ulinebuf[j] = BLANK;
00448
00449
00450
00451 cup->ulinemax = cup->ulinecnt;
00452 }
00453
00454
00455
00456
00457
00458
00459
00460 if ((cup->ulinecnt + field) > cup->urecsize) {
00461
00462 if ((cup->ulinecnt + width) > cup->urecsize) {
00463 stat = FEWRLONG;
00464 goto done;
00465 }
00466 else {
00467 kount = 1;
00468 field = width;
00469 }
00470 }
00471 }
00472
00473 switch (fmtop) {
00474
00475
00476
00477 case B_ED:
00478 case O_ED:
00479 case Z_ED:
00480 case D_ED:
00481 case E_ED:
00482 case EN_ED:
00483 case ES_ED:
00484 case F_ED:
00485 case G_ED:
00486 case I_ED:
00487 case L_ED:
00488
00489 ngcf = _oconvtab[fmtop];
00490
00491 #ifdef _CRAY
00492 #pragma _CRI align
00493 #endif
00494
00495 for (i = 0; i < kount; i++) {
00496
00497
00498
00499 if (supflg && (_o_sup_val_tab[type] == *(long *) cptr)) {
00500 register short j;
00501
00502 #ifdef _CRAY1
00503 #pragma _CRI ivdep
00504 #endif
00505 for (j = 0; j < width; j++)
00506 cup->ulineptr[j] = BLANK;
00507 }
00508 else
00509 (void) ngcf(cptr, cup->ulineptr, &mode,
00510 &width, &digits, &exp,
00511 &css->u.fmt.u.fe.scale);
00512
00513
00514
00515 cup->ulineptr = cup->ulineptr + width;
00516 count = count - part;
00517 cptr = cptr + cinc[part];
00518 part = part ^ cswitch;
00519 }
00520
00521 cup->ulinecnt = cup->ulinecnt + field;
00522
00523
00524
00525 if (cup->ulinecnt > cup->ulinemax)
00526 cup->ulinemax = cup->ulinecnt;
00527
00528 repcnt = repcnt - kount;
00529
00530 break;
00531
00532
00533
00534 case A_ED:
00535 case R_ED:
00536
00537 delta = width - length;
00538
00539
00540
00541
00542
00543
00544
00545 if (delta == 0 && tip->stride == 1) {
00546 register short knt;
00547
00548 (void) _unpack(cptr, cup->ulineptr, field, -1);
00549
00550 cup->ulineptr = cup->ulineptr + field;
00551 knt = kount >> cswitch;
00552
00553 if (cswitch != 0 && ((kount & 01) != 0)) {
00554
00555
00556
00557 count = count - part;
00558 cptr = cptr + cinc[part];
00559 part = part ^ 1;
00560 }
00561
00562 count = count - knt;
00563 cptr = cptr + (stride * knt);
00564 }
00565 else
00566
00567 #ifdef _CRAY
00568 #pragma _CRI align
00569 #endif
00570
00571 for (i = 0; i < kount; i++) {
00572
00573 ctmp = cptr;
00574
00575
00576
00577
00578
00579
00580
00581 if (delta > 0) {
00582 register short j;
00583
00584
00585
00586 for (j = 0; j < delta; j++)
00587 cup->ulineptr[j] = BLANK;
00588
00589
00590
00591 (void) _unpack(ctmp, cup->ulineptr + delta,
00592 length, -1);
00593 }
00594 else {
00595
00596
00597
00598
00599
00600
00601
00602 if (fmtop == R_ED)
00603 ctmp = ctmp - delta;
00604
00605
00606
00607 (void) _unpack(ctmp, cup->ulineptr, width, -1);
00608 }
00609
00610
00611
00612 cup->ulineptr = cup->ulineptr + width;
00613 count = count - part;
00614 cptr = cptr + cinc[part];
00615 part = part ^ cswitch;
00616 }
00617
00618 cup->ulinecnt = cup->ulinecnt + field;
00619
00620
00621
00622 if (cup->ulinecnt > cup->ulinemax)
00623 cup->ulinemax = cup->ulinecnt;
00624
00625 repcnt = repcnt - kount;
00626
00627 break;
00628
00629 case SLASH_ED:
00630 stat = (*css->u.fmt.endrec)(css, cup, width);
00631 repcnt = repcnt - 1;
00632 break;
00633
00634 case TR_ED:
00635 cup->ulinecnt = cup->ulinecnt + width;
00636 cup->ulineptr = cup->ulineptr + width;
00637 repcnt = repcnt - 1;
00638 break;
00639
00640 case T_ED:
00641 cup->ulinecnt = width - 1;
00642 cup->ulineptr = cup->ulinebuf + (width - 1);
00643 repcnt = 1;
00644 goto check_left;
00645
00646 case TL_ED:
00647 cup->ulinecnt = cup->ulinecnt - width;
00648 cup->ulineptr = cup->ulineptr - width;
00649 check_left:
00650
00651
00652
00653
00654 if (cup->ulineptr < css->u.fmt.leftablim) {
00655 cup->ulineptr = css->u.fmt.leftablim;
00656 cup->ulinecnt = cup->ulineptr - cup->ulinebuf;
00657 }
00658
00659 repcnt = repcnt - 1;
00660 break;
00661
00662 case STRING_ED:
00663 ctmp = (char *) (css->u.fmt.u.fe.pfcp + 1);
00664
00665 if (width > 0) {
00666
00667
00668
00669 for (i = 0; i < kount; i++) {
00670
00671 (void) _unpack(ctmp, cup->ulineptr, width, -1);
00672
00673 cup->ulineptr = cup->ulineptr + width;
00674 }
00675
00676 cup->ulinecnt = cup->ulinecnt + field;
00677
00678
00679
00680 if (cup->ulinecnt > cup->ulinemax)
00681 cup->ulinemax = cup->ulinecnt;
00682 }
00683
00684 repcnt = repcnt - kount;
00685 break;
00686
00687 case BN_ED:
00688 case BZ_ED:
00689 repcnt = 0;
00690 break;
00691
00692 case S_ED:
00693 case SS_ED:
00694 css->u.fmt.cplus = 0;
00695 dfmode = dfmode & ~MODESN;
00696 repcnt = 0;
00697 break;
00698
00699 case SP_ED:
00700 css->u.fmt.cplus = 1;
00701 dfmode = dfmode | MODESN;
00702 repcnt = 0;
00703 break;
00704
00705 case P_ED:
00706 css->u.fmt.u.fe.scale = pfmt.rep_count;
00707 repcnt = 0;
00708 break;
00709
00710 case Q_ED:
00711
00712
00713
00714 stat = FEFMTQIO;
00715 repcnt = repcnt - 1;
00716 break;
00717
00718 case COLON_ED:
00719
00720
00721
00722
00723
00724 if (count == 0)
00725 goto done;
00726
00727 repcnt = 0;
00728 break;
00729
00730 case DOLLAR_ED:
00731 css->u.fmt.nonl = 1;
00732 repcnt = 0;
00733 break;
00734
00735 case REPEAT_OP:
00736
00737
00738
00739
00740 *css->u.fmt.u.fe.pftocs++ = pfmt.rep_count;
00741 repcnt = 0;
00742 break;
00743
00744 case ENDREP_OP:
00745
00746
00747
00748
00749
00750
00751
00752
00753 if ( --(*(css->u.fmt.u.fe.pftocs - 1)) < 1)
00754 css->u.fmt.u.fe.pftocs--;
00755 else
00756 css->u.fmt.u.fe.pfcp = css->u.fmt.u.fe.pfcp +
00757 pfmt.rep_count;
00758 repcnt = repcnt - 1;
00759
00760 break;
00761
00762 case REVERT_OP:
00763
00764
00765
00766
00767
00768
00769 if (pfmt.rgcdedf == 0 && count > 0)
00770 stat = FEFMTILF;
00771 else {
00772
00773
00774
00775
00776
00777
00778
00779
00780
00781
00782
00783 if (count == 0)
00784 goto done;
00785
00786
00787
00788 stat = (*css->u.fmt.endrec)(css, cup, 1);
00789
00790 repcnt = 0;
00791
00792
00793
00794 css->u.fmt.u.fe.pfcp = css->u.fmt.u.fe.pfcp +
00795 pfmt.rep_count - 1;
00796 }
00797 break;
00798
00799 default:
00800 stat = FEINTIPF;
00801 break;
00802
00803 }
00804
00805
00806
00807
00808
00809
00810 if (stat == 0 && repcnt < 1) {
00811
00812 if (fmtop == STRING_ED)
00813 css->u.fmt.u.fe.pfcp = css->u.fmt.u.fe.pfcp +
00814 ((width +
00815 FMT_ENTRY_BYTE_SIZE - 1) /
00816 FMT_ENTRY_BYTE_SIZE);
00817
00818 css->u.fmt.u.fe.pfcp = css->u.fmt.u.fe.pfcp + 1;
00819 pfmt = *css->u.fmt.u.fe.pfcp;
00820 fmtop = pfmt.op_code;
00821 width = pfmt.field_width;
00822 repcnt = pfmt.rep_count;
00823 css->u.fmt.u.fe.fmtcol = pfmt.offset;
00824 }
00825
00826 } while (stat == 0);
00827 done:
00828
00829 #ifdef _CRAYT3D
00830 continue;
00831 } while (stat == 0 && shared && offset < tcount);
00832 #endif
00833
00834
00835
00836 *css->u.fmt.u.fe.pftocs = repcnt;
00837
00838
00839
00840 if (stat > 0 && (cup->uflag & (_UERRF | _UIOSTF)) == 0)
00841 _ferr(css, stat);
00842
00843 return(stat);
00844 }