Skip to content

AFNI/NIfTI Server

Sections
Personal tools
You are here: Home » AFNI » Documentation

Doxygen Source Code Documentation


Main Page   Alphabetical List   Data Structures   File List   Data Fields   Globals   Search  

io.c

Go to the documentation of this file.
00001 /****************************************************************
00002 Copyright 1990, 1991, 1993, 1994, 1996 by AT&T, Lucent Technologies and Bellcore.
00003 
00004 Permission to use, copy, modify, and distribute this software
00005 and its documentation for any purpose and without fee is hereby
00006 granted, provided that the above copyright notice appear in all
00007 copies and that both that the copyright notice and this
00008 permission notice and warranty disclaimer appear in supporting
00009 documentation, and that the names of AT&T, Bell Laboratories,
00010 Lucent or Bellcore or any of their entities not be used in
00011 advertising or publicity pertaining to distribution of the
00012 software without specific, written prior permission.
00013 
00014 AT&T, Lucent and Bellcore disclaim all warranties with regard to
00015 this software, including all implied warranties of
00016 merchantability and fitness.  In no event shall AT&T, Lucent or
00017 Bellcore be liable for any special, indirect or consequential
00018 damages or any damages whatsoever resulting from loss of use,
00019 data or profits, whether in an action of contract, negligence or
00020 other tortious action, arising out of or in connection with the
00021 use or performance of this software.
00022 ****************************************************************/
00023 
00024 /* Routines to generate code for I/O statements.
00025    Some corrections and improvements due to David Wasley, U. C. Berkeley
00026 */
00027 
00028 /* TEMPORARY */
00029 #define TYIOINT TYLONG
00030 #define SZIOINT SZLONG
00031 
00032 #include "defs.h"
00033 #include "names.h"
00034 #include "iob.h"
00035 
00036 extern int byterev, inqmask;
00037 
00038 static void dofclose Argdcl((void));
00039 static void dofinquire Argdcl((void));
00040 static void dofmove Argdcl((char*));
00041 static void dofopen Argdcl((void));
00042 static void doiolist Argdcl((chainp));
00043 static void ioset Argdcl((int, int, expptr));
00044 static void ioseta Argdcl((int, Addrp));
00045 static void iosetc Argdcl((int, expptr));
00046 static void iosetip Argdcl((int, int));
00047 static void iosetlc Argdcl((int, int, int));
00048 static void putio Argdcl((expptr, expptr));
00049 static void putiocall Argdcl((expptr));
00050 
00051 iob_data *iob_list;
00052 Addrp io_structs[9];
00053 
00054 LOCAL char ioroutine[12];
00055 
00056 LOCAL long ioendlab;
00057 LOCAL long ioerrlab;
00058 LOCAL int endbit;
00059 LOCAL int errbit;
00060 LOCAL long jumplab;
00061 LOCAL long skiplab;
00062 LOCAL int ioformatted;
00063 LOCAL int statstruct = NO;
00064 LOCAL struct Labelblock *skiplabel;
00065 Addrp ioblkp;
00066 
00067 #define UNFORMATTED 0
00068 #define FORMATTED 1
00069 #define LISTDIRECTED 2
00070 #define NAMEDIRECTED 3
00071 
00072 #define V(z)    ioc[z].iocval
00073 
00074 #define IOALL 07777
00075 
00076 LOCAL struct Ioclist
00077 {
00078         char *iocname;
00079         int iotype;
00080         expptr iocval;
00081 }
00082 ioc[ ] =
00083 {
00084         { "", 0 },
00085         { "unit", IOALL },
00086         { "fmt", M(IOREAD) | M(IOWRITE) },
00087         { "err", IOALL },
00088         { "end", M(IOREAD) },
00089         { "iostat", IOALL },
00090         { "rec", M(IOREAD) | M(IOWRITE) },
00091         { "recl", M(IOOPEN) | M(IOINQUIRE) },
00092         { "file", M(IOOPEN) | M(IOINQUIRE) },
00093         { "status", M(IOOPEN) | M(IOCLOSE) },
00094         { "access", M(IOOPEN) | M(IOINQUIRE) },
00095         { "form", M(IOOPEN) | M(IOINQUIRE) },
00096         { "blank", M(IOOPEN) | M(IOINQUIRE) },
00097         { "exist", M(IOINQUIRE) },
00098         { "opened", M(IOINQUIRE) },
00099         { "number", M(IOINQUIRE) },
00100         { "named", M(IOINQUIRE) },
00101         { "name", M(IOINQUIRE) },
00102         { "sequential", M(IOINQUIRE) },
00103         { "direct", M(IOINQUIRE) },
00104         { "formatted", M(IOINQUIRE) },
00105         { "unformatted", M(IOINQUIRE) },
00106         { "nextrec", M(IOINQUIRE) },
00107         { "nml", M(IOREAD) | M(IOWRITE) }
00108 };
00109 
00110 #define NIOS (sizeof(ioc)/sizeof(struct Ioclist) - 1)
00111 
00112 /* #define IOSUNIT 1 */
00113 /* #define IOSFMT 2 */
00114 #define IOSERR 3
00115 #define IOSEND 4
00116 #define IOSIOSTAT 5
00117 #define IOSREC 6
00118 #define IOSRECL 7
00119 #define IOSFILE 8
00120 #define IOSSTATUS 9
00121 #define IOSACCESS 10
00122 #define IOSFORM 11
00123 #define IOSBLANK 12
00124 #define IOSEXISTS 13
00125 #define IOSOPENED 14
00126 #define IOSNUMBER 15
00127 #define IOSNAMED 16
00128 #define IOSNAME 17
00129 #define IOSSEQUENTIAL 18
00130 #define IOSDIRECT 19
00131 #define IOSFORMATTED 20
00132 #define IOSUNFORMATTED 21
00133 #define IOSNEXTREC 22
00134 #define IOSNML 23
00135 
00136 #define IOSTP V(IOSIOSTAT)
00137 
00138 
00139 /* offsets in generated structures */
00140 
00141 #define SZFLAG SZIOINT
00142 
00143 /* offsets for external READ and WRITE statements */
00144 
00145 #define XERR 0
00146 #define XUNIT   SZFLAG
00147 #define XEND    SZFLAG + SZIOINT
00148 #define XFMT    2*SZFLAG + SZIOINT
00149 #define XREC    2*SZFLAG + SZIOINT + SZADDR
00150 
00151 /* offsets for internal READ and WRITE statements */
00152 
00153 #define XIUNIT  SZFLAG
00154 #define XIEND   SZFLAG + SZADDR
00155 #define XIFMT   2*SZFLAG + SZADDR
00156 #define XIRLEN  2*SZFLAG + 2*SZADDR
00157 #define XIRNUM  2*SZFLAG + 2*SZADDR + SZIOINT
00158 #define XIREC   2*SZFLAG + 2*SZADDR + 2*SZIOINT
00159 
00160 /* offsets for OPEN statements */
00161 
00162 #define XFNAME  SZFLAG + SZIOINT
00163 #define XFNAMELEN       SZFLAG + SZIOINT + SZADDR
00164 #define XSTATUS SZFLAG + 2*SZIOINT + SZADDR
00165 #define XACCESS SZFLAG + 2*SZIOINT + 2*SZADDR
00166 #define XFORMATTED      SZFLAG + 2*SZIOINT + 3*SZADDR
00167 #define XRECLEN SZFLAG + 2*SZIOINT + 4*SZADDR
00168 #define XBLANK  SZFLAG + 3*SZIOINT + 4*SZADDR
00169 
00170 /* offset for CLOSE statement */
00171 
00172 #define XCLSTATUS       SZFLAG + SZIOINT
00173 
00174 /* offsets for INQUIRE statement */
00175 
00176 #define XFILE   SZFLAG + SZIOINT
00177 #define XFILELEN        SZFLAG + SZIOINT + SZADDR
00178 #define XEXISTS SZFLAG + 2*SZIOINT + SZADDR
00179 #define XOPEN   SZFLAG + 2*SZIOINT + 2*SZADDR
00180 #define XNUMBER SZFLAG + 2*SZIOINT + 3*SZADDR
00181 #define XNAMED  SZFLAG + 2*SZIOINT + 4*SZADDR
00182 #define XNAME   SZFLAG + 2*SZIOINT + 5*SZADDR
00183 #define XNAMELEN        SZFLAG + 2*SZIOINT + 6*SZADDR
00184 #define XQACCESS        SZFLAG + 3*SZIOINT + 6*SZADDR
00185 #define XQACCLEN        SZFLAG + 3*SZIOINT + 7*SZADDR
00186 #define XSEQ    SZFLAG + 4*SZIOINT + 7*SZADDR
00187 #define XSEQLEN SZFLAG + 4*SZIOINT + 8*SZADDR
00188 #define XDIRECT SZFLAG + 5*SZIOINT + 8*SZADDR
00189 #define XDIRLEN SZFLAG + 5*SZIOINT + 9*SZADDR
00190 #define XFORM   SZFLAG + 6*SZIOINT + 9*SZADDR
00191 #define XFORMLEN        SZFLAG + 6*SZIOINT + 10*SZADDR
00192 #define XFMTED  SZFLAG + 7*SZIOINT + 10*SZADDR
00193 #define XFMTEDLEN       SZFLAG + 7*SZIOINT + 11*SZADDR
00194 #define XUNFMT  SZFLAG + 8*SZIOINT + 11*SZADDR
00195 #define XUNFMTLEN       SZFLAG + 8*SZIOINT + 12*SZADDR
00196 #define XQRECL  SZFLAG + 9*SZIOINT + 12*SZADDR
00197 #define XNEXTREC        SZFLAG + 9*SZIOINT + 13*SZADDR
00198 #define XQBLANK SZFLAG + 9*SZIOINT + 14*SZADDR
00199 #define XQBLANKLEN      SZFLAG + 9*SZIOINT + 15*SZADDR
00200 
00201 LOCAL char *cilist_names[] = {
00202         "cilist",
00203         "cierr",
00204         "ciunit",
00205         "ciend",
00206         "cifmt",
00207         "cirec"
00208         };
00209 LOCAL char *icilist_names[] = {
00210         "icilist",
00211         "icierr",
00212         "iciunit",
00213         "iciend",
00214         "icifmt",
00215         "icirlen",
00216         "icirnum"
00217         };
00218 LOCAL char *olist_names[] = {
00219         "olist",
00220         "oerr",
00221         "ounit",
00222         "ofnm",
00223         "ofnmlen",
00224         "osta",
00225         "oacc",
00226         "ofm",
00227         "orl",
00228         "oblnk"
00229         };
00230 LOCAL char *cllist_names[] = {
00231         "cllist",
00232         "cerr",
00233         "cunit",
00234         "csta"
00235         };
00236 LOCAL char *alist_names[] = {
00237         "alist",
00238         "aerr",
00239         "aunit"
00240         };
00241 LOCAL char *inlist_names[] = {
00242         "inlist",
00243         "inerr",
00244         "inunit",
00245         "infile",
00246         "infilen",
00247         "inex",
00248         "inopen",
00249         "innum",
00250         "innamed",
00251         "inname",
00252         "innamlen",
00253         "inacc",
00254         "inacclen",
00255         "inseq",
00256         "inseqlen",
00257         "indir",
00258         "indirlen",
00259         "infmt",
00260         "infmtlen",
00261         "inform",
00262         "informlen",
00263         "inunf",
00264         "inunflen",
00265         "inrecl",
00266         "innrec",
00267         "inblank",
00268         "inblanklen"
00269         };
00270 
00271 LOCAL char **io_fields;
00272 
00273 #define zork(n,t) n, sizeof(n)/sizeof(char *) - 1, t
00274 
00275 LOCAL io_setup io_stuff[] = {
00276         zork(cilist_names, TYCILIST),   /* external read/write */
00277         zork(inlist_names, TYINLIST),   /* inquire */
00278         zork(olist_names,  TYOLIST),    /* open */
00279         zork(cllist_names, TYCLLIST),   /* close */
00280         zork(alist_names,  TYALIST),    /* rewind */
00281         zork(alist_names,  TYALIST),    /* backspace */
00282         zork(alist_names,  TYALIST),    /* endfile */
00283         zork(icilist_names,TYICILIST),  /* internal read */
00284         zork(icilist_names,TYICILIST)   /* internal write */
00285         };
00286 
00287 #undef zork
00288 
00289  int
00290 #ifdef KR_headers
00291 fmtstmt(lp)
00292         register struct Labelblock *lp;
00293 #else
00294 fmtstmt(register struct Labelblock *lp)
00295 #endif
00296 {
00297         if(lp == NULL)
00298         {
00299                 execerr("unlabeled format statement" , CNULL);
00300                 return(-1);
00301         }
00302         if(lp->labtype == LABUNKNOWN)
00303         {
00304                 lp->labtype = LABFORMAT;
00305                 lp->labelno = (int)newlabel();
00306         }
00307         else if(lp->labtype != LABFORMAT)
00308         {
00309                 execerr("bad format number", CNULL);
00310                 return(-1);
00311         }
00312         return(lp->labelno);
00313 }
00314 
00315 
00316  void
00317 #ifdef KR_headers
00318 setfmt(lp)
00319         struct Labelblock *lp;
00320 #else
00321 setfmt(struct Labelblock *lp)
00322 #endif
00323 {
00324         int n, parity;
00325         char *s0;
00326         register char *s, *se, *t;
00327         register k;
00328 
00329         s0 = s = lexline(&n);
00330         se = t = s + n;
00331 
00332         /* warn of trivial errors, e.g. "  11 CONTINUE" (one too few spaces) */
00333         /* following FORMAT... */
00334 
00335         if (n <= 0)
00336                 warn("No (...) after FORMAT");
00337         else if (*s != '(')
00338                 warni("%c rather than ( after FORMAT", *s);
00339         else if (se[-1] != ')') {
00340                 *se = 0;
00341                 while(--t > s && *t != ')') ;
00342                 if (t <= s)
00343                         warn("No ) at end of FORMAT statement");
00344                 else if (se - t > 30)
00345                         warn1("Extraneous text at end of FORMAT: ...%s", se-12);
00346                 else
00347                         warn1("Extraneous text at end of FORMAT: %s", t+1);
00348                 t = se;
00349                 }
00350 
00351         /* fix MYQUOTES (\002's) and \\'s */
00352 
00353         parity = 1;
00354         while(s < se)
00355                 switch(*s++) {
00356                         case 2:
00357                                 if ((parity ^= 1) && *s == 2) {
00358                                         t -= 2;
00359                                         ++s;
00360                                         }
00361                                 else
00362                                         t += 3;
00363                                 break;
00364                         case '"':
00365                         case '\\':
00366                                 t++; break;
00367                         }
00368         s = s0;
00369         parity = 1;
00370         if (lp) {
00371                 lp->fmtstring = t = mem((int)(t - s + 1), 0);
00372                 while(s < se)
00373                         switch(k = *s++) {
00374                                 case 2:
00375                                         if ((parity ^= 1) && *s == 2)
00376                                                 s++;
00377                                         else {
00378                                                 t[0] = '\\';
00379                                                 t[1] = '0';
00380                                                 t[2] = '0';
00381                                                 t[3] = '2';
00382                                                 t += 4;
00383                                                 }
00384                                         break;
00385                                 case '"':
00386                                 case '\\':
00387                                         *t++ = '\\';
00388                                         /* no break */
00389                                 default:
00390                                         *t++ = k;
00391                                 }
00392                 *t = 0;
00393                 }
00394         flline();
00395 }
00396 
00397 
00398  void
00399 #ifdef KR_headers
00400 startioctl()
00401 #else
00402 startioctl()
00403 #endif
00404 {
00405         register int i;
00406 
00407         inioctl = YES;
00408         nioctl = 0;
00409         ioformatted = UNFORMATTED;
00410         for(i = 1 ; i<=NIOS ; ++i)
00411                 V(i) = NULL;
00412 }
00413 
00414  static long
00415 newiolabel(Void) {
00416         long rv;
00417         rv = ++lastiolabno;
00418         skiplabel = mklabel(rv);
00419         skiplabel->labdefined = 1;
00420         return rv;
00421         }
00422 
00423  void
00424 endioctl(Void)
00425 {
00426         int i;
00427         expptr p;
00428         struct io_setup *ios;
00429 
00430         inioctl = NO;
00431 
00432         /* set up for error recovery */
00433 
00434         ioerrlab = ioendlab = skiplab = jumplab = 0;
00435 
00436         if(p = V(IOSEND))
00437                 if(ISICON(p))
00438                         execlab(ioendlab = p->constblock.Const.ci);
00439                 else
00440                         err("bad end= clause");
00441 
00442         if(p = V(IOSERR))
00443                 if(ISICON(p))
00444                         execlab(ioerrlab = p->constblock.Const.ci);
00445                 else
00446                         err("bad err= clause");
00447 
00448         if(IOSTP)
00449                 if(IOSTP->tag!=TADDR || ! ISINT(IOSTP->addrblock.vtype) )
00450                 {
00451                         err("iostat must be an integer variable");
00452                         frexpr(IOSTP);
00453                         IOSTP = NULL;
00454                 }
00455 
00456         if(iostmt == IOREAD)
00457         {
00458                 if(IOSTP)
00459                 {
00460                         if(ioerrlab && ioendlab && ioerrlab==ioendlab)
00461                                 jumplab = ioerrlab;
00462                         else
00463                                 skiplab = jumplab = newiolabel();
00464                 }
00465                 else    {
00466                         if(ioerrlab && ioendlab && ioerrlab!=ioendlab)
00467                         {
00468                                 IOSTP = (expptr) mktmp(TYINT, ENULL);
00469                                 skiplab = jumplab = newiolabel();
00470                         }
00471                         else
00472                                 jumplab = (ioerrlab ? ioerrlab : ioendlab);
00473                 }
00474         }
00475         else if(iostmt == IOWRITE)
00476         {
00477                 if(IOSTP && !ioerrlab)
00478                         skiplab = jumplab = newiolabel();
00479                 else
00480                         jumplab = ioerrlab;
00481         }
00482         else
00483                 jumplab = ioerrlab;
00484 
00485         endbit = IOSTP!=NULL || ioendlab!=0;    /* for use in startrw() */
00486         errbit = IOSTP!=NULL || ioerrlab!=0;
00487         if (jumplab && !IOSTP)
00488                 IOSTP = (expptr) mktmp(TYINT, ENULL);
00489 
00490         if(iostmt!=IOREAD && iostmt!=IOWRITE)
00491         {
00492                 ios = io_stuff + iostmt;
00493                 io_fields = ios->fields;
00494                 ioblkp = io_structs[iostmt];
00495                 if(ioblkp == NULL)
00496                         io_structs[iostmt] = ioblkp =
00497                                 autovar(1, ios->type, ENULL, "");
00498                 ioset(TYIOINT, XERR, ICON(errbit));
00499         }
00500 
00501         switch(iostmt)
00502         {
00503         case IOOPEN:
00504                 dofopen();
00505                 break;
00506 
00507         case IOCLOSE:
00508                 dofclose();
00509                 break;
00510 
00511         case IOINQUIRE:
00512                 dofinquire();
00513                 break;
00514 
00515         case IOBACKSPACE:
00516                 dofmove("f_back");
00517                 break;
00518 
00519         case IOREWIND:
00520                 dofmove("f_rew");
00521                 break;
00522 
00523         case IOENDFILE:
00524                 dofmove("f_end");
00525                 break;
00526 
00527         case IOREAD:
00528         case IOWRITE:
00529                 startrw();
00530                 break;
00531 
00532         default:
00533                 fatali("impossible iostmt %d", iostmt);
00534         }
00535         for(i = 1 ; i<=NIOS ; ++i)
00536                 if(i!=IOSIOSTAT && V(i)!=NULL)
00537                         frexpr(V(i));
00538 }
00539 
00540 
00541  int
00542 iocname(Void)
00543 {
00544         register int i;
00545         int found, mask;
00546 
00547         found = 0;
00548         mask = M(iostmt);
00549         for(i = 1 ; i <= NIOS ; ++i)
00550                 if(!strcmp(ioc[i].iocname, token))
00551                         if(ioc[i].iotype & mask)
00552                                 return(i);
00553                         else {
00554                                 found = i;
00555                                 break;
00556                                 }
00557         if(found) {
00558                 if (iostmt == IOOPEN && !strcmp(ioc[i].iocname, "name")) {
00559                         NOEXT("open with \"name=\" treated as \"file=\"");
00560                         for(i = 1; strcmp(ioc[i].iocname, "file"); i++);
00561                         return i;
00562                         }
00563                 errstr("invalid control %s for statement", ioc[found].iocname);
00564                 }
00565         else
00566                 errstr("unknown iocontrol %s", token);
00567         return(IOSBAD);
00568 }
00569 
00570 
00571  void
00572 #ifdef KR_headers
00573 ioclause(n, p)
00574         register int n;
00575         register expptr p;
00576 #else
00577 ioclause(register int n, register expptr p)
00578 #endif
00579 {
00580         struct Ioclist *iocp;
00581 
00582         ++nioctl;
00583         if(n == IOSBAD)
00584                 return;
00585         if(n == IOSPOSITIONAL)
00586                 {
00587                 n = nioctl;
00588                 if (n == IOSFMT) {
00589                         if (iostmt == IOOPEN) {
00590                                 n = IOSFILE;
00591                                 NOEXT("file= specifier omitted from open");
00592                                 }
00593                         else if (iostmt < IOREAD)
00594                                 goto illegal;
00595                         }
00596                 else if(n > IOSFMT)
00597                         {
00598  illegal:
00599                         err("illegal positional iocontrol");
00600                         return;
00601                         }
00602                 }
00603         else if (n == IOSNML)
00604                 n = IOSFMT;
00605 
00606         if(p == NULL)
00607         {
00608                 if(n == IOSUNIT)
00609                         p = (expptr) (iostmt==IOREAD ? IOSTDIN : IOSTDOUT);
00610                 else if(n != IOSFMT)
00611                 {
00612                         err("illegal * iocontrol");
00613                         return;
00614                 }
00615         }
00616         if(n == IOSFMT)
00617                 ioformatted = (p==NULL ? LISTDIRECTED : FORMATTED);
00618 
00619         iocp = & ioc[n];
00620         if(iocp->iocval == NULL)
00621         {
00622                 if(n!=IOSFMT && ( n!=IOSUNIT || (p && p->headblock.vtype!=TYCHAR) ) )
00623                         p = fixtype(p);
00624                 else if (p && p->tag == TPRIM
00625                            && p->primblock.namep->vclass == CLUNKNOWN) {
00626                         /* kludge made necessary by attempt to infer types
00627                          * for untyped external parameters: given an error
00628                          * in calling sequences, an integer argument might
00629                          * tentatively be assumed TYCHAR; this would otherwise
00630                          * be corrected too late in startrw after startrw
00631                          * had decided this to be an internal file.
00632                          */
00633                         vardcl(p->primblock.namep);
00634                         p->primblock.vtype = p->primblock.namep->vtype;
00635                         }
00636                 iocp->iocval = p;
00637         }
00638         else
00639                 errstr("iocontrol %s repeated", iocp->iocname);
00640 }
00641 
00642 /* io list item */
00643 
00644  void
00645 #ifdef KR_headers
00646 doio(list)
00647         chainp list;
00648 #else
00649 doio(chainp list)
00650 #endif
00651 {
00652         if(ioformatted == NAMEDIRECTED)
00653         {
00654                 if(list)
00655                         err("no I/O list allowed in NAMELIST read/write");
00656         }
00657         else
00658         {
00659                 doiolist(list);
00660                 ioroutine[0] = 'e';
00661                 if (skiplab)
00662                         jumplab = 0;
00663                 putiocall( call0(TYINT, ioroutine) );
00664         }
00665 }
00666 
00667 
00668 
00669 
00670 
00671  LOCAL void
00672 #ifdef KR_headers
00673 doiolist(p0)
00674         chainp p0;
00675 #else
00676 doiolist(chainp p0)
00677 #endif
00678 {
00679         chainp p;
00680         register tagptr q;
00681         register expptr qe;
00682         register Namep qn;
00683         Addrp tp;
00684         int range;
00685         extern char *ohalign;
00686 
00687         for (p = p0 ; p ; p = p->nextp)
00688         {
00689                 q = (tagptr)p->datap;
00690                 if(q->tag == TIMPLDO)
00691                 {
00692                         exdo(range = (int)newlabel(), (Namep)0,
00693                                 q->impldoblock.impdospec);
00694                         doiolist(q->impldoblock.datalist);
00695                         enddo(range);
00696                         free( (charptr) q);
00697                 }
00698                 else    {
00699                         if(q->tag==TPRIM && q->primblock.argsp==NULL
00700                             && q->primblock.namep->vdim!=NULL)
00701                         {
00702                                 vardcl(qn = q->primblock.namep);
00703                                 if(qn->vdim->nelt) {
00704                                         putio( fixtype(cpexpr(qn->vdim->nelt)),
00705                                             (expptr)mkscalar(qn) );
00706                                         qn->vlastdim = 0;
00707                                         }
00708                                 else
00709                                         err("attempt to i/o array of unknown size");
00710                         }
00711                         else if(q->tag==TPRIM && q->primblock.argsp==NULL &&
00712                             (qe = (expptr) memversion(q->primblock.namep)) )
00713                                 putio(ICON(1),qe);
00714                         else if (ISCONST(q) && q->constblock.vtype == TYCHAR) {
00715                                 halign = 0;
00716                                 putio(ICON(1), qe = fixtype(cpexpr(q)));
00717                                 halign = ohalign;
00718                                 }
00719                         else if(((qe = fixtype(cpexpr(q)))->tag==TADDR &&
00720                             (qe->addrblock.uname_tag != UNAM_CONST ||
00721                             !ISCOMPLEX(qe -> addrblock.vtype))) ||
00722                             (qe -> tag == TCONST && !ISCOMPLEX(qe ->
00723                             headblock.vtype))) {
00724                                 if (qe -> tag == TCONST)
00725                                         qe = (expptr) putconst((Constp)qe);
00726                                 putio(ICON(1), qe);
00727                         }
00728                         else if(qe->headblock.vtype != TYERROR)
00729                         {
00730                                 if(iostmt == IOWRITE)
00731                                 {
00732                                         expptr qvl;
00733                                         qvl = NULL;
00734                                         if( ISCHAR(qe) )
00735                                         {
00736                                                 qvl = (expptr)
00737                                                     cpexpr(qe->headblock.vleng);
00738                                                 tp = mktmp(qe->headblock.vtype,
00739                                                     ICON(lencat(qe)));
00740                                         }
00741                                         else
00742                                                 tp = mktmp(qe->headblock.vtype,
00743                                                     qe->headblock.vleng);
00744                                         puteq( cpexpr((expptr)tp), qe);
00745                                         if(qvl) /* put right length on block */
00746                                         {
00747                                                 frexpr(tp->vleng);
00748                                                 tp->vleng = qvl;
00749                                         }
00750                                         putio(ICON(1), (expptr)tp);
00751                                 }
00752                                 else
00753                                         err("non-left side in READ list");
00754                         }
00755                         frexpr(q);
00756                 }
00757         }
00758         frchain( &p0 );
00759 }
00760 
00761  int iocalladdr = TYADDR;       /* for fixing TYADDR in saveargtypes */
00762  int typeconv[TYERROR+1] = {
00763 #ifdef TYQUAD
00764                 0, 1, 11, 2, 3, 14, 4, 5, 6, 7, 12, 13, 8, 9, 10, 15
00765 #else
00766                 0, 1, 11, 2, 3,     4, 5, 6, 7, 12, 13, 8, 9, 10, 14
00767 #endif
00768                 };
00769 
00770  LOCAL void
00771 #ifdef KR_headers
00772 putio(nelt, addr)
00773         expptr nelt;
00774         register expptr addr;
00775 #else
00776 putio(expptr nelt, register expptr addr)
00777 #endif
00778 {
00779         int type;
00780         register expptr q;
00781         register Addrp c = 0;
00782 
00783         type = addr->headblock.vtype;
00784         if(ioformatted!=LISTDIRECTED && ISCOMPLEX(type) )
00785         {
00786                 nelt = mkexpr(OPSTAR, ICON(2), nelt);
00787                 type -= (TYCOMPLEX-TYREAL);
00788         }
00789 
00790         /* pass a length with every item.  for noncharacter data, fake one */
00791         if(type != TYCHAR)
00792         {
00793 
00794                 if( ISCONST(addr) )
00795                         addr = (expptr) putconst((Constp)addr);
00796                 c = ALLOC(Addrblock);
00797                 c->tag = TADDR;
00798                 c->vtype = TYLENG;
00799                 c->vstg = STGAUTO;
00800                 c->ntempelt = 1;
00801                 c->isarray = 1;
00802                 c->memoffset = ICON(0);
00803                 c->uname_tag = UNAM_IDENT;
00804                 c->charleng = 1;
00805                 sprintf(c->user.ident, "(ftnlen)sizeof(%s)", typename[type]);
00806                 addr = mkexpr(OPCHARCAST, addr, ENULL);
00807                 }
00808 
00809         nelt = fixtype( mkconv(tyioint,nelt) );
00810         if(ioformatted == LISTDIRECTED) {
00811                 expptr mc = mkconv(tyioint, ICON(typeconv[type]));
00812                 q = c   ? call4(TYINT, "do_lio", mc, nelt, addr, (expptr)c)
00813                         : call3(TYINT, "do_lio", mc, nelt, addr);
00814                 }
00815         else {
00816                 char *s = ioformatted==FORMATTED ? "do_fio"
00817                         : !byterev ? "do_uio"
00818                         : ONEOF(type, M(TYCHAR)|M(TYINT1)|M(TYLOGICAL1))
00819                         ? "do_ucio" : "do_unio";
00820                 q = c   ? call3(TYINT, s, nelt, addr, (expptr)c)
00821                         : call2(TYINT, s, nelt, addr);
00822                 }
00823         iocalladdr = TYCHAR;
00824         putiocall(q);
00825         iocalladdr = TYADDR;
00826 }
00827 
00828 
00829 
00830  void
00831 endio(Void)
00832 {
00833         if(skiplab)
00834         {
00835                 if (ioformatted != NAMEDIRECTED)
00836                         p1_label((long)(skiplabel - labeltab));
00837                 if(ioendlab) {
00838                         exif( mkexpr(OPLT, cpexpr(IOSTP), ICON(0)));
00839                         exgoto(execlab(ioendlab));
00840                         exendif();
00841                         }
00842                 if(ioerrlab) {
00843                         exif( mkexpr(iostmt==IOREAD||iostmt==IOWRITE
00844                                         ? OPGT : OPNE,
00845                                 cpexpr(IOSTP), ICON(0)));
00846                         exgoto(execlab(ioerrlab));
00847                         exendif();
00848                         }
00849         }
00850 
00851         if(IOSTP)
00852                 frexpr(IOSTP);
00853 }
00854 
00855 
00856 
00857  LOCAL void
00858 #ifdef KR_headers
00859 putiocall(q)
00860         register expptr q;
00861 #else
00862 putiocall(register expptr q)
00863 #endif
00864 {
00865         int tyintsave;
00866 
00867         tyintsave = tyint;
00868         tyint = tyioint;        /* for -I2 and -i2 */
00869 
00870         if(IOSTP)
00871         {
00872                 q->headblock.vtype = TYINT;
00873                 q = fixexpr((Exprp)mkexpr(OPASSIGN, cpexpr(IOSTP), q));
00874         }
00875         putexpr(q);
00876         if(jumplab) {
00877                 exif(mkexpr(OPNE, cpexpr(IOSTP), ICON(0)));
00878                 exgoto(execlab(jumplab));
00879                 exendif();
00880                 }
00881         tyint = tyintsave;
00882 }
00883 
00884  void
00885 #ifdef KR_headers
00886 fmtname(np, q)
00887         Namep np;
00888         register Addrp q;
00889 #else
00890 fmtname(Namep np, register Addrp q)
00891 #endif
00892 {
00893         register int k;
00894         register char *s, *t;
00895         extern chainp assigned_fmts;
00896 
00897         if (!np->vfmt_asg) {
00898                 np->vfmt_asg = 1;
00899                 assigned_fmts = mkchain((char *)np, assigned_fmts);
00900                 }
00901         k = strlen(s = np->fvarname);
00902         if (k < IDENT_LEN - 4) {
00903                 q->uname_tag = UNAM_IDENT;
00904                 t = q->user.ident;
00905                 }
00906         else {
00907                 q->uname_tag = UNAM_CHARP;
00908                 q->user.Charp = t = mem(k + 5,0);
00909                 }
00910         sprintf(t, "%s_fmt", s);
00911         }
00912 
00913  LOCAL Addrp
00914 #ifdef KR_headers
00915 asg_addr(p)
00916         union Expression *p;
00917 #else
00918 asg_addr(union Expression *p)
00919 #endif
00920 {
00921         register Addrp q;
00922 
00923         if (p->tag != TPRIM)
00924                 badtag("asg_addr", p->tag);
00925         q = ALLOC(Addrblock);
00926         q->tag = TADDR;
00927         q->vtype = TYCHAR;
00928         q->vstg = STGAUTO;
00929         q->ntempelt = 1;
00930         q->isarray = 0;
00931         q->memoffset = ICON(0);
00932         fmtname(p->primblock.namep, q);
00933         return q;
00934         }
00935 
00936  void
00937 startrw(Void)
00938 {
00939         register expptr p;
00940         register Namep np;
00941         register Addrp unitp, fmtp, recp;
00942         register expptr nump;
00943         int iostmt1;
00944         flag intfile, sequential, ok, varfmt;
00945         struct io_setup *ios;
00946 
00947         /* First look at all the parameters and determine what is to be done */
00948 
00949         ok = YES;
00950         statstruct = YES;
00951 
00952         intfile = NO;
00953         if(p = V(IOSUNIT))
00954         {
00955                 if( ISINT(p->headblock.vtype) ) {
00956  int_unit:
00957                         unitp = (Addrp) cpexpr(p);
00958                         }
00959                 else if(p->headblock.vtype == TYCHAR)
00960                 {
00961                         if (nioctl == 1 && iostmt == IOREAD) {
00962                                 /* kludge to recognize READ(format expr) */
00963                                 V(IOSFMT) = p;
00964                                 V(IOSUNIT) = p = (expptr) IOSTDIN;
00965                                 ioformatted = FORMATTED;
00966                                 goto int_unit;
00967                                 }
00968                         intfile = YES;
00969                         if(p->tag==TPRIM && p->primblock.argsp==NULL &&
00970                             (np = p->primblock.namep)->vdim!=NULL)
00971                         {
00972                                 vardcl(np);
00973                                 if(nump = np->vdim->nelt)
00974                                 {
00975                                         nump = fixtype(cpexpr(nump));
00976                                         if( ! ISCONST(nump) ) {
00977                                                 statstruct = NO;
00978                                                 np->vlastdim = 0;
00979                                                 }
00980                                 }
00981                                 else
00982                                 {
00983                                         err("attempt to use internal unit array of unknown size");
00984                                         ok = NO;
00985                                         nump = ICON(1);
00986                                 }
00987                                 unitp = mkscalar(np);
00988                         }
00989                         else    {
00990                                 nump = ICON(1);
00991                                 unitp = (Addrp /*pjw */) fixtype(cpexpr(p));
00992                         }
00993                         if(! isstatic((expptr)unitp) )
00994                                 statstruct = NO;
00995                 }
00996                 else {
00997                         err("unit specifier not of type integer or character");
00998                         ok = NO;
00999                         }
01000         }
01001         else
01002         {
01003                 err("bad unit specifier");
01004                 ok = NO;
01005         }
01006 
01007         sequential = YES;
01008         if(p = V(IOSREC))
01009                 if( ISINT(p->headblock.vtype) )
01010                 {
01011                         recp = (Addrp) cpexpr(p);
01012                         sequential = NO;
01013                 }
01014                 else    {
01015                         err("bad REC= clause");
01016                         ok = NO;
01017                 }
01018         else
01019                 recp = NULL;
01020 
01021 
01022         varfmt = YES;
01023         fmtp = NULL;
01024         if(p = V(IOSFMT))
01025         {
01026                 if(p->tag==TPRIM && p->primblock.argsp==NULL)
01027                 {
01028                         np = p->primblock.namep;
01029                         if(np->vclass == CLNAMELIST)
01030                         {
01031                                 ioformatted = NAMEDIRECTED;
01032                                 fmtp = (Addrp) fixtype(p);
01033                                 V(IOSFMT) = (expptr)fmtp;
01034                                 if (skiplab)
01035                                         jumplab = 0;
01036                                 goto endfmt;
01037                         }
01038                         vardcl(np);
01039                         if(np->vdim)
01040                         {
01041                                 if( ! ONEOF(np->vstg, MSKSTATIC) )
01042                                         statstruct = NO;
01043                                 fmtp = mkscalar(np);
01044                                 goto endfmt;
01045                         }
01046                         if( ISINT(np->vtype) )  /* ASSIGNed label */
01047                         {
01048                                 statstruct = NO;
01049                                 varfmt = YES;
01050                                 fmtp = asg_addr(p);
01051                                 goto endfmt;
01052                         }
01053                 }
01054                 p = V(IOSFMT) = fixtype(p);
01055                 if(p->headblock.vtype == TYCHAR
01056                         /* Since we allow write(6,n)            */
01057                         /* we may as well allow write(6,n(2))   */
01058                 || p->tag == TADDR && ISINT(p->addrblock.vtype))
01059                 {
01060                         if( ! isstatic(p) )
01061                                 statstruct = NO;
01062                         fmtp = (Addrp) cpexpr(p);
01063                 }
01064                 else if( ISICON(p) )
01065                 {
01066                         struct Labelblock *lp;
01067                         lp = mklabel(p->constblock.Const.ci);
01068                         if (fmtstmt(lp) > 0)
01069                         {
01070                                 fmtp = (Addrp)mkaddcon(lp->stateno);
01071                                 /* lp->stateno for names fmt_nnn */
01072                                 lp->fmtlabused = 1;
01073                                 varfmt = NO;
01074                         }
01075                         else
01076                                 ioformatted = UNFORMATTED;
01077                 }
01078                 else    {
01079                         err("bad format descriptor");
01080                         ioformatted = UNFORMATTED;
01081                         ok = NO;
01082                 }
01083         }
01084         else
01085                 fmtp = NULL;
01086 
01087 endfmt:
01088         if(intfile) {
01089                 if (ioformatted==UNFORMATTED) {
01090                         err("unformatted internal I/O not allowed");
01091                         ok = NO;
01092                         }
01093                 if (recp) {
01094                         err("direct internal I/O not allowed");
01095                         ok = NO;
01096                         }
01097                 }
01098         if(!sequential && ioformatted==LISTDIRECTED)
01099         {
01100                 err("direct list-directed I/O not allowed");
01101                 ok = NO;
01102         }
01103         if(!sequential && ioformatted==NAMEDIRECTED)
01104         {
01105                 err("direct namelist I/O not allowed");
01106                 ok = NO;
01107         }
01108 
01109         if( ! ok ) {
01110                 statstruct = NO;
01111                 return;
01112                 }
01113 
01114         /*
01115    Now put out the I/O structure, statically if all the clauses
01116    are constants, dynamically otherwise
01117 */
01118 
01119         if (intfile) {
01120                 ios = io_stuff + iostmt;
01121                 iostmt1 = IOREAD;
01122                 }
01123         else {
01124                 ios = io_stuff;
01125                 iostmt1 = 0;
01126                 }
01127         io_fields = ios->fields;
01128         if(statstruct)
01129         {
01130                 ioblkp = ALLOC(Addrblock);
01131                 ioblkp->tag = TADDR;
01132                 ioblkp->vtype = ios->type;
01133                 ioblkp->vclass = CLVAR;
01134                 ioblkp->vstg = STGINIT;
01135                 ioblkp->memno = ++lastvarno;
01136                 ioblkp->memoffset = ICON(0);
01137                 ioblkp -> uname_tag = UNAM_IDENT;
01138                 new_iob_data(ios,
01139                         temp_name("io_", lastvarno, ioblkp->user.ident));                       }
01140         else if(!(ioblkp = io_structs[iostmt1]))
01141                 io_structs[iostmt1] = ioblkp =
01142                         autovar(1, ios->type, ENULL, "");
01143 
01144         ioset(TYIOINT, XERR, ICON(errbit));
01145         if(iostmt == IOREAD)
01146                 ioset(TYIOINT, (intfile ? XIEND : XEND), ICON(endbit) );
01147 
01148         if(intfile)
01149         {
01150                 ioset(TYIOINT, XIRNUM, nump);
01151                 ioset(TYIOINT, XIRLEN, cpexpr(unitp->vleng) );
01152                 ioseta(XIUNIT, unitp);
01153         }
01154         else
01155                 ioset(TYIOINT, XUNIT, (expptr) unitp);
01156 
01157         if(recp)
01158                 ioset(TYIOINT, /* intfile ? XIREC : */ XREC, (expptr) recp);
01159 
01160         if(varfmt)
01161                 ioseta( intfile ? XIFMT : XFMT , fmtp);
01162         else
01163                 ioset(TYADDR, intfile ? XIFMT : XFMT, (expptr) fmtp);
01164 
01165         ioroutine[0] = 's';
01166         ioroutine[1] = '_';
01167         ioroutine[2] = iostmt==IOREAD ? 'r' : 'w';
01168         ioroutine[3] = "ds"[sequential];
01169         ioroutine[4] = "ufln"[ioformatted];
01170         ioroutine[5] = "ei"[intfile];
01171         ioroutine[6] = '\0';
01172 
01173         putiocall( call1(TYINT, ioroutine, cpexpr((expptr)ioblkp) ));
01174 
01175         if(statstruct)
01176         {
01177                 frexpr((expptr)ioblkp);
01178                 statstruct = NO;
01179                 ioblkp = 0;     /* unnecessary */
01180         }
01181 }
01182 
01183 
01184 
01185  LOCAL void
01186 dofopen(Void)
01187 {
01188         register expptr p;
01189 
01190         if( (p = V(IOSUNIT)) && ISINT(p->headblock.vtype) )
01191                 ioset(TYIOINT, XUNIT, cpexpr(p) );
01192         else
01193                 err("bad unit in open");
01194         if( (p = V(IOSFILE)) )
01195                 if(p->headblock.vtype == TYCHAR)
01196                         ioset(TYIOINT, XFNAMELEN, cpexpr(p->headblock.vleng) );
01197                 else
01198                         err("bad file in open");
01199 
01200         iosetc(XFNAME, p);
01201 
01202         if(p = V(IOSRECL))
01203                 if( ISINT(p->headblock.vtype) )
01204                         ioset(TYIOINT, XRECLEN, cpexpr(p) );
01205                 else
01206                         err("bad recl");
01207         else
01208                 ioset(TYIOINT, XRECLEN, ICON(0) );
01209 
01210         iosetc(XSTATUS, V(IOSSTATUS));
01211         iosetc(XACCESS, V(IOSACCESS));
01212         iosetc(XFORMATTED, V(IOSFORM));
01213         iosetc(XBLANK, V(IOSBLANK));
01214 
01215         putiocall( call1(TYINT, "f_open", cpexpr((expptr)ioblkp) ));
01216 }
01217 
01218 
01219  LOCAL void
01220 dofclose(Void)
01221 {
01222         register expptr p;
01223 
01224         if( (p = V(IOSUNIT)) && ISINT(p->headblock.vtype) )
01225         {
01226                 ioset(TYIOINT, XUNIT, cpexpr(p) );
01227                 iosetc(XCLSTATUS, V(IOSSTATUS));
01228                 putiocall( call1(TYINT, "f_clos", cpexpr((expptr)ioblkp)) );
01229         }
01230         else
01231                 err("bad unit in close statement");
01232 }
01233 
01234 
01235  LOCAL void
01236 dofinquire(Void)
01237 {
01238         register expptr p;
01239         if(p = V(IOSUNIT))
01240         {
01241                 if( V(IOSFILE) )
01242                         err("inquire by unit or by file, not both");
01243                 ioset(TYIOINT, XUNIT, cpexpr(p) );
01244         }
01245         else if( ! V(IOSFILE) )
01246                 err("must inquire by unit or by file");
01247         iosetlc(IOSFILE, XFILE, XFILELEN);
01248         iosetip(IOSEXISTS, XEXISTS);
01249         iosetip(IOSOPENED, XOPEN);
01250         iosetip(IOSNUMBER, XNUMBER);
01251         iosetip(IOSNAMED, XNAMED);
01252         iosetlc(IOSNAME, XNAME, XNAMELEN);
01253         iosetlc(IOSACCESS, XQACCESS, XQACCLEN);
01254         iosetlc(IOSSEQUENTIAL, XSEQ, XSEQLEN);
01255         iosetlc(IOSDIRECT, XDIRECT, XDIRLEN);
01256         iosetlc(IOSFORM, XFORM, XFORMLEN);
01257         iosetlc(IOSFORMATTED, XFMTED, XFMTEDLEN);
01258         iosetlc(IOSUNFORMATTED, XUNFMT, XUNFMTLEN);
01259         iosetip(IOSRECL, XQRECL);
01260         iosetip(IOSNEXTREC, XNEXTREC);
01261         iosetlc(IOSBLANK, XQBLANK, XQBLANKLEN);
01262 
01263         putiocall( call1(TYINT,  "f_inqu", cpexpr((expptr)ioblkp) ));
01264 }
01265 
01266 
01267 
01268  LOCAL void
01269 #ifdef KR_headers
01270 dofmove(subname)
01271         char *subname;
01272 #else
01273 dofmove(char *subname)
01274 #endif
01275 {
01276         register expptr p;
01277 
01278         if( (p = V(IOSUNIT)) && ISINT(p->headblock.vtype) )
01279         {
01280                 ioset(TYIOINT, XUNIT, cpexpr(p) );
01281                 putiocall( call1(TYINT, subname, cpexpr((expptr)ioblkp) ));
01282         }
01283         else
01284                 err("bad unit in I/O motion statement");
01285 }
01286 
01287 static int ioset_assign = OPASSIGN;
01288 
01289  LOCAL void
01290 #ifdef KR_headers
01291 ioset(type, offset, p)
01292         int type;
01293         int offset;
01294         register expptr p;
01295 #else
01296 ioset(int type, int offset, register expptr p)
01297 #endif
01298 {
01299         offset /= SZLONG;
01300         if(statstruct && ISCONST(p)) {
01301                 register char *s;
01302                 switch(type) {
01303                         case TYADDR:    /* stmt label */
01304                                 s = "fmt_";
01305                                 break;
01306                         case TYIOINT:
01307                                 s = "";
01308                                 break;
01309                         default:
01310                                 badtype("ioset", type);
01311                         }
01312                 iob_list->fields[offset] =
01313                         string_num(s, p->constblock.Const.ci);
01314                 frexpr(p);
01315                 }
01316         else {
01317                 register Addrp q;
01318 
01319                 q = ALLOC(Addrblock);
01320                 q->tag = TADDR;
01321                 q->vtype = type;
01322                 q->vstg = STGAUTO;
01323                 q->ntempelt = 1;
01324                 q->isarray = 0;
01325                 q->memoffset = ICON(0);
01326                 q->uname_tag = UNAM_IDENT;
01327                 sprintf(q->user.ident, "%s.%s",
01328                         statstruct ? iob_list->name : ioblkp->user.ident,
01329                         io_fields[offset + 1]);
01330                 if (type == TYADDR && p->tag == TCONST
01331                                    && p->constblock.vtype == TYADDR) {
01332                         /* kludge */
01333                         register Addrp p1;
01334                         p1 = ALLOC(Addrblock);
01335                         p1->tag = TADDR;
01336                         p1->vtype = type;
01337                         p1->vstg = STGAUTO;     /* wrong, but who cares? */
01338                         p1->ntempelt = 1;
01339                         p1->isarray = 0;
01340                         p1->memoffset = ICON(0);
01341                         p1->uname_tag = UNAM_IDENT;
01342                         sprintf(p1->user.ident, "fmt_%ld",
01343                                 p->constblock.Const.ci);
01344                         frexpr(p);
01345                         p = (expptr)p1;
01346                         }
01347                 if (type == TYADDR && p->headblock.vtype == TYCHAR)
01348                         q->vtype = TYCHAR;
01349                 putexpr(mkexpr(ioset_assign, (expptr)q, p));
01350                 }
01351 }
01352 
01353 
01354 
01355 
01356  LOCAL void
01357 #ifdef KR_headers
01358 iosetc(offset, p)
01359         int offset;
01360         register expptr p;
01361 #else
01362 iosetc(int offset, register expptr p)
01363 #endif
01364 {
01365         if(p == NULL)
01366                 ioset(TYADDR, offset, ICON(0) );
01367         else if(p->headblock.vtype == TYCHAR) {
01368                 p = putx(fixtype((expptr)putchop(cpexpr(p))));
01369                 ioset(TYADDR, offset, addrof(p));
01370                 }
01371         else
01372                 err("non-character control clause");
01373 }
01374 
01375 
01376 
01377  LOCAL void
01378 #ifdef KR_headers
01379 ioseta(offset, p)
01380         int offset;
01381         register Addrp p;
01382 #else
01383 ioseta(int offset, register Addrp p)
01384 #endif
01385 {
01386         char *s, *s1;
01387         static char who[] = "ioseta";
01388         expptr e, mo;
01389         Namep np;
01390         ftnint ci;
01391         int k;
01392         char buf[24], buf1[24];
01393         Extsym *comm;
01394         extern int usedefsforcommon;
01395 
01396         if(statstruct)
01397         {
01398                 if (!p)
01399                         return;
01400                 if (p->tag != TADDR)
01401                         badtag(who, p->tag);
01402                 offset /= SZLONG;
01403                 switch(p->uname_tag) {
01404                     case UNAM_NAME:
01405                         mo = p->memoffset;
01406                         if (mo->tag != TCONST)
01407                                 badtag("ioseta/memoffset", mo->tag);
01408                         np = p->user.name;
01409                         np->visused = 1;
01410                         ci = mo->constblock.Const.ci - np->voffset;
01411                         if (np->vstg == STGCOMMON
01412                         && !np->vcommequiv
01413                         && !usedefsforcommon) {
01414                                 comm = &extsymtab[np->vardesc.varno];
01415                                 sprintf(buf, "%d.", comm->curno);
01416                                 k = strlen(buf) + strlen(comm->cextname)
01417                                         + strlen(np->cvarname);
01418                                 if (ci) {
01419                                         sprintf(buf1, "+%ld", ci);
01420                                         k += strlen(buf1);
01421                                         }
01422                                 else
01423                                         buf1[0] = 0;
01424                                 s = mem(k + 1, 0);
01425                                 sprintf(s, "%s%s%s%s", comm->cextname, buf,
01426                                         np->cvarname, buf1);
01427                                 }
01428                         else if (ci) {
01429                                 sprintf(buf,"%ld", ci);
01430                                 s1 = p->user.name->cvarname;
01431                                 k = strlen(buf) + strlen(s1);
01432                                 sprintf(s = mem(k+2,0), "%s+%s", s1, buf);
01433                                 }
01434                         else
01435                                 s = cpstring(np->cvarname);
01436                         break;
01437                     case UNAM_CONST:
01438                         s = tostring(p->user.Const.ccp1.ccp0,
01439                                 (int)p->vleng->constblock.Const.ci);
01440                         break;
01441                     default:
01442                         badthing("uname_tag", who, p->uname_tag);
01443                     }
01444                 /* kludge for Hollerith */
01445                 if (p->vtype != TYCHAR) {
01446                         s1 = mem(strlen(s)+10,0);
01447                         sprintf(s1, "(char *)%s%s", p->isarray ? "" : "&", s);
01448                         s = s1;
01449                         }
01450                 iob_list->fields[offset] = s;
01451         }
01452         else {
01453                 if (!p)
01454                         e = ICON(0);
01455                 else if (p->vtype != TYCHAR) {
01456                         NOEXT("non-character variable as format or internal unit");
01457                         e = mkexpr(OPCHARCAST, (expptr)p, ENULL);
01458                         }
01459                 else
01460                         e = addrof((expptr)p);
01461                 ioset(TYADDR, offset, e);
01462                 }
01463 }
01464 
01465 
01466 
01467 
01468  LOCAL void
01469 #ifdef KR_headers
01470 iosetip(i, offset)
01471         int i;
01472         int offset;
01473 #else
01474 iosetip(int i, int offset)
01475 #endif
01476 {
01477         register expptr p;
01478 
01479         if(p = V(i))
01480                 if(p->tag==TADDR &&
01481                     ONEOF(p->addrblock.vtype, inqmask) ) {
01482                         ioset_assign = OPASSIGNI;
01483                         ioset(TYADDR, offset, addrof(cpexpr(p)) );
01484                         ioset_assign = OPASSIGN;
01485                         }
01486                 else
01487                         errstr("impossible inquire parameter %s", ioc[i].iocname);
01488         else
01489                 ioset(TYADDR, offset, ICON(0) );
01490 }
01491 
01492 
01493 
01494  LOCAL void
01495 #ifdef KR_headers
01496 iosetlc(i, offp, offl)
01497         int i;
01498         int offp;
01499         int offl;
01500 #else
01501 iosetlc(int i, int offp, int offl)
01502 #endif
01503 {
01504         register expptr p;
01505         if( (p = V(i)) && p->headblock.vtype==TYCHAR)
01506                 ioset(TYIOINT, offl, cpexpr(p->headblock.vleng) );
01507         iosetc(offp, p);
01508 }
 

Powered by Plone

This site conforms to the following standards: