xref: /original-bsd/usr.bin/pascal/src/0.h (revision d6141097)
1 /* Copyright (c) 1979 Regents of the University of California */
2 
3 /* static char sccsid[] = "@(#)0.h 1.16 10/19/82"; */
4 
5 #define DEBUG
6 #define CONSETS
7 #define	CHAR
8 #define	STATIC
9 #define hp21mx 0
10 
11 #include	<stdio.h>
12 #include	<sys/types.h>
13 
14 typedef enum {FALSE, TRUE} bool;
15 
16 /*
17  * Option flags
18  *
19  * The following options are recognized in the text of the program
20  * and also on the command line:
21  *
22  *	b	block buffer the file output
23  *
24  *	i	make a listing of the procedures and functions in
25  *		the following include files
26  *
27  *	l	make a listing of the program
28  *
29  *	n	place each include file on a new page with a header
30  *
31  *	p	disable post mortem and statement limit counting
32  *
33  *	t	disable run-time tests
34  *
35  *	u	card image mode; only first 72 chars of input count
36  *
37  *	w	suppress special diagnostic warnings
38  *
39  *	z	generate counters for an execution profile
40  */
41 #ifdef DEBUG
42 bool	fulltrace, errtrace, testtrace, yyunique;
43 #endif DEBUG
44 
45 /*
46  * Each option has a stack of 17 option values, with opts giving
47  * the current, top value, and optstk the value beneath it.
48  * One refers to option `l' as, e.g., opt('l') in the text for clarity.
49  */
50 char	opts[ 'z' - 'A' + 1];
51 short	optstk[ 'z' - 'A' + 1];
52 
53 #define opt(c) opts[c-'A']
54 
55 /*
56  * Monflg is set when we are generating
57  * a pxp profile.  this is set by the -z command line option.
58  */
59 bool	monflg;
60 
61     /*
62      *	profflag is set when we are generating a prof profile.
63      *	this is set by the -p command line option.
64      */
65 bool	profflag;
66 
67 
68 /*
69  * NOTES ON THE DYNAMIC NATURE OF THE DATA STRUCTURES
70  *
71  * Pi uses expandable tables for
72  * its namelist (symbol table), string table
73  * hash table, and parse tree space.  The following
74  * definitions specify the size of the increments
75  * for these items in fundamental units so that
76  * each uses approximately 1024 bytes.
77  */
78 
79 #define	STRINC	1024		/* string space increment */
80 #define	TRINC	512		/* tree space increment */
81 #define	HASHINC	509		/* hash table size in words, each increment */
82 #define	NLINC	56		/* namelist increment size in nl structs */
83 
84 /*
85  * The initial sizes of the structures.
86  * These should be large enough to compile
87  * an "average" sized program so as to minimize
88  * storage requests.
89  * On a small system or and 11/34 or 11/40
90  * these numbers can be trimmed to make the
91  * compiler smaller.
92  */
93 #define	ITREE	2000
94 #define	INL	200
95 #define	IHASH	509
96 
97 /*
98  * The following limits on hash and tree tables currently
99  * allow approximately 1200 symbols and 20k words of tree
100  * space.  The fundamental limit of 64k total data space
101  * should be exceeded well before these are full.
102  */
103 /*
104  * TABLE_MULTIPLIER is for uniformly increasing the sizes of the tables
105  */
106 #ifdef VAX
107 #define TABLE_MULTIPLIER	8
108 #else
109 #define TABLE_MULTIPLIER	1
110 #endif VAX
111 #define	MAXHASH	(4 * TABLE_MULTIPLIER)
112 #define	MAXNL	(12 * TABLE_MULTIPLIER)
113 #define	MAXTREE	(30 * TABLE_MULTIPLIER)
114 /*
115  * MAXDEPTH is the depth of the parse stack.
116  * STACK_MULTIPLIER is for increasing its size.
117  */
118 #ifdef VAX
119 #define	STACK_MULTIPLIER	8
120 #else
121 #define	STACK_MULTIPLIER	1
122 #endif VAX
123 #define	MAXDEPTH ( 150 * STACK_MULTIPLIER )
124 
125 /*
126  * ERROR RELATED DEFINITIONS
127  */
128 
129 /*
130  * Exit statuses to pexit
131  *
132  * AOK
133  * ERRS		Compilation errors inhibit obj productin
134  * NOSTART	Errors before we ever got started
135  * DIED		We ran out of memory or some such
136  */
137 #define	AOK	0
138 #define	ERRS	1
139 #define	NOSTART	2
140 #define	DIED	3
141 
142 bool	Recovery;
143 
144 #define	eholdnl()	Eholdnl = 1
145 #define	nocascade()	Enocascade = 1
146 
147 bool	Eholdnl, Enocascade;
148 
149 
150 /*
151  * The flag eflg is set whenever we have a hard error.
152  * The character in errpfx will precede the next error message.
153  * When cgenflg is set code generation is suppressed.
154  * This happens whenver we have an error (i.e. if eflg is set)
155  * and when we are walking the tree to determine types only.
156  */
157 bool	eflg;
158 char	errpfx;
159 
160 #define	setpfx(x)	errpfx = x
161 
162 #define	standard()	setpfx('s')
163 #define	warning()	setpfx('w')
164 #define	recovered()	setpfx('e')
165 #define	continuation()	setpfx(' ')
166 
167 int	cgenflg;
168 
169 
170 /*
171  * The flag syneflg is used to suppress the diagnostics of the form
172  *	E 10 a, defined in someprocedure, is neither used nor set
173  * when there were syntax errors in "someprocedure".
174  * In this case, it is likely that these warinings would be spurious.
175  */
176 bool	syneflg;
177 
178 /*
179  * The compiler keeps its error messages in a file.
180  * The variable efil is the unit number on which
181  * this file is open for reading of error message text.
182  * Similarly, the file ofil is the unit of the file
183  * "obj" where we write the interpreter code.
184  */
185 short	efil;
186 short	ofil;
187 short	obuf[518];
188 
189 bool	Enoline;
190 #define	elineoff()	Enoline = TRUE
191 #define	elineon()	Enoline = FALSE
192 
193 
194 /*
195  * SYMBOL TABLE STRUCTURE DEFINITIONS
196  *
197  * The symbol table is henceforth referred to as the "namelist".
198  * It consists of a number of structures of the form "nl" below.
199  * These are contained in a number of segments of the symbol
200  * table which are dynamically allocated as needed.
201  * The major namelist manipulation routines are contained in the
202  * file "nl.c".
203  *
204  * The major components of a namelist entry are the "symbol", giving
205  * a pointer into the string table for the string associated with this
206  * entry and the "class" which tells which of the (currently 19)
207  * possible types of structure this is.
208  *
209  * Many of the classes use the "type" field for a pointer to the type
210  * which the entry has.
211  *
212  * Other pieces of information in more than one class include the block
213  * in which the symbol is defined, flags indicating whether the symbol
214  * has been used and whether it has been assigned to, etc.
215  *
216  * A more complete discussion of the features of the namelist is impossible
217  * here as it would be too voluminous.  Refer to the "PI 1.0 Implementation
218  * Notes" for more details.
219  */
220 
221 /*
222  * The basic namelist structure.
223  * There is a union of data types defining the stored information
224  * as pointers, integers, longs, or a double.
225  *
226  * The array disptab defines the hash header for the symbol table.
227  * Symbols are hashed based on the low 6 bits of their pointer into
228  * the string table; see the routines in the file "lookup.c" and also "fdec.c"
229  * especially "funcend".
230  */
231 extern int	pnumcnt;
232 
233 #ifdef PTREE
234 #   include	"pTree.h"
235 #endif PTREE
236 struct	nl {
237 	char	*symbol;
238 	char	info[4];
239 	struct	nl *type;
240 	struct	nl *chain, *nl_next;
241 	union {
242 		int	*un_ptr[5];
243 		int	un_value[5];
244 		long	un_range[2];
245 		double	un_real;
246 	} nl_un;
247 #	ifdef PTREE
248 	    pPointer	inTree;
249 #	endif PTREE
250 };
251 
252 #define class		info[0]
253 #define nl_flags	info[1]
254 #define nl_block	info[1]
255 #define extra_flags	info[2]
256 #define align_info	info[3]
257 
258 #define range	nl_un.un_range
259 #define value	nl_un.un_value
260 #define ptr	nl_un.un_ptr
261 #define real	nl_un.un_real
262 
263 extern struct nl *nlp, *disptab[077+1], *Fp;
264 extern struct nl nl[INL];
265 
266 
267 /*
268  * NL FLAGS BITS
269  *
270  * Definitions of the usage of the bits in
271  * the nl_flags byte. Note that the low 5 bits of the
272  * byte are the "nl_block" and that some classes make use
273  * of this byte as a "width".
274  *
275  * The only non-obvious bit definition here is "NFILES"
276  * which records whether a structure contains any files.
277  * Such structures are not allowed to be dynamically allocated.
278  */
279 
280 #define	BLOCKNO( flag )	( flag & 037 )
281 #define NLFLAGS( flag ) ( flag &~ 037 )
282 
283 #define	NUSED	0100
284 #define	NMOD	0040
285 #define	NFORWD	0200
286 #define	NFILES	0200
287 #ifdef PC
288 #define NEXTERN 0001	/* flag used to mark external funcs and procs */
289 #define	NLOCAL	0002	/* variable is a local */
290 #define	NPARAM	0004	/* variable is a parameter */
291 #define	NGLOBAL	0010	/* variable is a global */
292 #define	NREGVAR	0020	/* or'ed in if variable is in a register */
293 #endif PC
294 
295 /*
296  * used to mark value[ NL_FORV ] for loop variables
297  */
298 #define	FORVAR		1
299 
300 /*
301  * Definition of the commonly used "value" fields.
302  * The most important one is NL_OFFS which gives
303  * the offset of a variable in its stack mark.
304  */
305 #define NL_OFFS	0
306 
307 #define	NL_CNTR	1
308 #define NL_NLSTRT 2
309 #define	NL_LINENO 3
310 #define	NL_FVAR	3
311 #define	NL_ENTLOC 4	/* FUNC, PROC - entry point */
312 #define	NL_FCHAIN 4	/* FFUNC, FPROC - ptr to formals */
313 
314 #define NL_GOLEV 2
315 #define NL_GOLINE 3
316 #define NL_FORV 1
317 
318     /*
319      *	nlp -> nl_un.un_ptr[] subscripts for records
320      *	NL_FIELDLIST	the chain of fixed fields of a record, in order.
321      *			the fields are also chained through ptr[NL_FIELDLIST].
322      *			this does not include the tag, or fields of variants.
323      *	NL_VARNT	pointer to the variants of a record,
324      *			these are then chained through the .chain field.
325      *	NL_VTOREC	pointer from a VARNT to the RECORD that is the variant.
326      *	NL_TAG		pointer from a RECORD to the tagfield
327      *			if there are any variants.
328      *	align_info	the alignment of a RECORD is in info[3].
329      */
330 #define	NL_FIELDLIST	1
331 #define	NL_VARNT	2
332 #define	NL_VTOREC	2
333 #define	NL_TAG		3
334 /* and align_info is info[3].  #defined above */
335 
336 #define	NL_ELABEL 4	/* SCAL - ptr to definition of enums */
337 
338 /*
339  * For BADUSE nl structures, NL_KINDS is a bit vector
340  * indicating the kinds of illegal usages complained about
341  * so far.  For kind of bad use "kind", "1 << kind" is set.
342  * The low bit is reserved as ISUNDEF to indicate whether
343  * this identifier is totally undefined.
344  */
345 #define	NL_KINDS	0
346 
347 #define	ISUNDEF		1
348 
349     /*
350      *	variables come in three flavors: globals, parameters, locals;
351      *	they can also hide in registers, but that's a different flag
352      */
353 #define PARAMVAR	1
354 #define LOCALVAR	2
355 #define	GLOBALVAR	3
356 
357 /*
358  * NAMELIST CLASSES
359  *
360  * The following are the namelist classes.
361  * Different classes make use of the value fields
362  * of the namelist in different ways.
363  *
364  * The namelist should be redesigned by providing
365  * a number of structure definitions with one corresponding
366  * to each namelist class, ala a variant record in Pascal.
367  */
368 #define	BADUSE	0
369 #define	CONST	1
370 #define	TYPE	2
371 #define	VAR	3
372 #define	ARRAY	4
373 #define	PTRFILE	5
374 #define	RECORD	6
375 #define	FIELD	7
376 #define	PROC	8
377 #define	FUNC	9
378 #define	FVAR	10
379 #define	REF	11
380 #define	PTR	12
381 #define	FILET	13
382 #define	SET	14
383 #define	RANGE	15
384 #define	LABEL	16
385 #define	WITHPTR 17
386 #define	SCAL	18
387 #define	STR	19
388 #define	PROG	20
389 #define	IMPROPER 21
390 #define	VARNT	22
391 #define	FPROC	23
392 #define	FFUNC	24
393 
394 /*
395  * Clnames points to an array of names for the
396  * namelist classes.
397  */
398 char	**clnames;
399 
400 /*
401  * PRE-DEFINED NAMELIST OFFSETS
402  *
403  * The following are the namelist offsets for the
404  * primitive types. The ones which are negative
405  * don't actually exist, but are generated and tested
406  * internally. These definitions are sensitive to the
407  * initializations in nl.c.
408  */
409 #define	TFIRST -7
410 #define	TFILE  -7
411 #define	TREC   -6
412 #define	TARY   -5
413 #define	TSCAL  -4
414 #define	TPTR   -3
415 #define	TSET   -2
416 #define	TSTR   -1
417 #define	NIL	0
418 #define	TBOOL	1
419 #define	TCHAR	2
420 #define	TINT	3
421 #define	TDOUBLE	4
422 #define	TNIL	5
423 #define	T1INT	6
424 #define	T2INT	7
425 #define	T4INT	8
426 #define	T1CHAR	9
427 #define	T1BOOL	10
428 #define	T8REAL	11
429 #define TLAST	11
430 
431 /*
432  * SEMANTIC DEFINITIONS
433  */
434 
435 /*
436  * NOCON and SAWCON are flags in the tree telling whether
437  * a constant set is part of an expression.
438  *	these are no longer used,
439  *	since we now do constant sets at compile time.
440  */
441 #define NOCON	0
442 #define SAWCON	1
443 
444 /*
445  * The variable cbn gives the current block number,
446  * the variable bn is set as a side effect of a call to
447  * lookup, and is the block number of the variable which
448  * was found.
449  */
450 short	bn, cbn;
451 
452 /*
453  * The variable line is the current semantic
454  * line and is set in stat.c from the numbers
455  * embedded in statement type tree nodes.
456  */
457 short	line;
458 
459 /*
460  * The size of the display
461  * which defines the maximum nesting
462  * of procedures and functions allowed.
463  * Because of the flags in the current namelist
464  * this must be no greater than 32.
465  */
466 #define	DSPLYSZ 20
467 
468     /*
469      *	the display is made up of saved AP's and FP's.
470      *	FP's are used to find locals, and AP's are used to find parameters.
471      *	FP and AP are untyped pointers, but are used throughout as (char *).
472      *	the display is used by adding AP_OFFSET or FP_OFFSET to the
473      *	address of the approriate display entry.
474      */
475 struct dispsave {
476     char	*savedAP;
477     char	*savedFP;
478 } display[ DSPLYSZ ];
479 
480 #define	AP_OFFSET	( 0 )
481 #define FP_OFFSET	( sizeof(char *) )
482 
483     /*
484      *	formal routine structure:
485      */
486 struct formalrtn {
487 	long		(*fentryaddr)();	/* formal entry point */
488 	long		fbn;			/* block number of function */
489 	struct dispsave	fdisp[ DSPLYSZ ];	/* saved at first passing */
490 } frtn;
491 
492 #define	FENTRYOFFSET	0
493 #define FBNOFFSET	( FENTRYOFFSET + sizeof frtn.fentryaddr )
494 #define	FDISPOFFSET	( FBNOFFSET + sizeof frtn.fbn )
495 
496 /*
497  * The following structure is used
498  * to keep track of the amount of variable
499  * storage required by each block.
500  * "Max" is the high water mark, "off"
501  * the current need. Temporaries for "for"
502  * loops and "with" statements are allocated
503  * in the local variable area and these
504  * numbers are thereby changed if necessary.
505  */
506 struct om {
507 	long	om_max;
508 	long	reg_max;
509 	struct tmps {
510 		long	om_off;
511 		long	reg_off;
512 	} curtmps;
513 } sizes[DSPLYSZ];
514 #define NOREG 0
515 #define REGOK 1
516 
517     /*
518      *	the following structure records whether a level declares
519      *	any variables which are (or contain) files.
520      *	this so that the runtime routines for file cleanup can be invoked.
521      */
522 bool	dfiles[ DSPLYSZ ];
523 
524 /*
525  * Structure recording information about a constant
526  * declaration.  It is actually the return value from
527  * the routine "gconst", but since C doesn't support
528  * record valued functions, this is more convenient.
529  */
530 struct {
531 	struct nl	*ctype;
532 	short		cival;
533 	double		crval;
534 	int		*cpval;
535 } con;
536 
537 /*
538  * The set structure records the lower bound
539  * and upper bound with the lower bound normalized
540  * to zero when working with a set. It is set by
541  * the routine setran in var.c.
542  */
543 struct {
544 	short	lwrb, uprbp;
545 } set;
546 
547     /*
548      *	structures of this kind are filled in by precset and used by postcset
549      *	to indicate things about constant sets.
550      */
551 struct csetstr {
552     struct nl	*csettype;
553     long	paircnt;
554     long	singcnt;
555     bool	comptime;
556 };
557 /*
558  * The following flags are passed on calls to lvalue
559  * to indicate how the reference is to affect the usage
560  * information for the variable being referenced.
561  * MOD is used to set the NMOD flag in the namelist
562  * entry for the variable, ASGN permits diagnostics
563  * to be formed when a for variable is assigned to in
564  * the range of the loop.
565  */
566 #define	NOFLAGS	0
567 #define	MOD	01
568 #define	ASGN	02
569 #define	NOUSE	04
570 
571     /*
572      *	the following flags are passed to lvalue and rvalue
573      *	to tell them whether an lvalue or rvalue is required.
574      *	the semantics checking is done according to the function called,
575      *	but for pc, lvalue may put out an rvalue by indirecting afterwards,
576      *	and rvalue may stop short of putting out the indirection.
577      */
578 #define	LREQ	01
579 #define	RREQ	02
580 
581 double	MAXINT;
582 double	MININT;
583 
584 /*
585  * Variables for generation of profile information.
586  * Monflg is set when we want to generate a profile.
587  * Gocnt record the total number of goto's and
588  * cnts records the current counter for generating
589  * COUNT operators.
590  */
591 short	gocnt;
592 short	cnts;
593 
594 /*
595  * Most routines call "incompat" rather than asking "!compat"
596  * for historical reasons.
597  */
598 #define incompat 	!compat
599 
600 /*
601  * Parts records which declaration parts have been seen.
602  * The grammar allows the "label" "const" "type" "var" and routine
603  * parts to be repeated and to be in any order, so that
604  * they can be detected semantically to give better
605  * error diagnostics.
606  */
607 int	parts[ DSPLYSZ ];
608 
609 #define	LPRT	1
610 #define	CPRT	2
611 #define	TPRT	4
612 #define	VPRT	8
613 #define	RPRT	16
614 
615 /*
616  * Flags for the "you used / instead of div" diagnostic
617  */
618 bool	divchk;
619 bool	divflg;
620 
621 bool	errcnt[DSPLYSZ];
622 
623 /*
624  * Forechain links those types which are
625  *	^ sometype
626  * so that they can be evaluated later, permitting
627  * circular, recursive list structures to be defined.
628  */
629 struct	nl *forechain;
630 
631 /*
632  * Withlist links all the records which are currently
633  * opened scopes because of with statements.
634  */
635 struct	nl *withlist;
636 
637 struct	nl *intset;
638 struct	nl *input, *output;
639 struct	nl *program;
640 
641 /* progseen flag used by PC to determine if
642  * a routine segment is being compiled (and
643  * therefore no program statement seen)
644  */
645 bool	progseen;
646 
647 
648 /*
649  * STRUCTURED STATEMENT GOTO CHECKING
650  *
651  * The variable level keeps track of the current
652  * "structured statement level" when processing the statement
653  * body of blocks.  This is used in the detection of goto's into
654  * structured statements in a block.
655  *
656  * Each label's namelist entry contains two pieces of information
657  * related to this check. The first `NL_GOLEV' either contains
658  * the level at which the label was declared, `NOTYET' if the label
659  * has not yet been declared, or `DEAD' if the label is dead, i.e.
660  * if we have exited the level in which the label was defined.
661  *
662  * When we discover a "goto" statement, if the label has not
663  * been defined yet, then we record the current level and the current line
664  * for a later error check.  If the label has been already become "DEAD"
665  * then a reference to it is an error.  Now the compiler maintains,
666  * for each block, a linked list of the labels headed by "gotos[bn]".
667  * When we exit a structured level, we perform the routine
668  * ungoto in stat.c. It notices labels whose definition levels have been
669  * exited and makes them be dead. For labels which have not yet been
670  * defined, ungoto will maintain NL_GOLEV as the minimum structured level
671  * since the first usage of the label. It is not hard to see that the label
672  * must eventually be declared at this level or an outer level to this
673  * one or a goto into a structured statement will exist.
674  */
675 short	level;
676 struct	nl *gotos[DSPLYSZ];
677 
678 #define	NOTYET	10000
679 #define	DEAD	10000
680 
681 /*
682  * Noreach is true when the next statement will
683  * be unreachable unless something happens along
684  * (like exiting a looping construct) to save
685  * the day.
686  */
687 bool	noreach;
688 
689 /*
690  * UNDEFINED VARIABLE REFERENCE STRUCTURES
691  */
692 struct	udinfo {
693 	int	ud_line;
694 	struct	udinfo *ud_next;
695 	char	nullch;
696 };
697 
698 /*
699  * CODE GENERATION DEFINITIONS
700  */
701 
702 /*
703  * NSTAND is or'ed onto the abstract machine opcode
704  * for non-standard built-in procedures and functions.
705  */
706 #define	NSTAND	0400
707 
708 #define	codeon()	cgenflg++
709 #define	codeoff()	--cgenflg
710 #define	CGENNING	( cgenflg >= 0 )
711 
712 /*
713  * Codeline is the last lino output in the code generator.
714  * It used to be used to suppress LINO operators but no
715  * more since we now count statements.
716  * Lc is the intepreter code location counter.
717  *
718 short	codeline;
719  */
720 char	*lc;
721 
722 
723 /*
724  * Routines which need types
725  * other than "integer" to be
726  * assumed by the compiler.
727  */
728 double		atof();
729 long		lwidth();
730 long		leven();
731 long		aryconst();
732 long		a8tol();
733 long		roundup();
734 struct nl 	*tmpalloc();
735 struct nl 	*lookup();
736 double		atof();
737 int		*tree();
738 int		*hash();
739 char		*alloc();
740 int		*calloc();
741 char		*savestr();
742 char		*parnam();
743 bool		fcompat();
744 struct nl	*lookup1();
745 struct nl	*hdefnl();
746 struct nl	*defnl();
747 struct nl	*enter();
748 struct nl	*nlcopy();
749 struct nl	*tyrec();
750 struct nl	*tyary();
751 struct nl	*deffld();
752 struct nl	*defvnt();
753 struct nl	*tyrec1();
754 struct nl	*reclook();
755 struct nl	*asgnop1();
756 struct nl	*gtype();
757 struct nl	*call();
758 struct nl	*lvalue();
759 struct nl	*rvalue();
760 struct nl	*cset();
761 
762 /*
763  * type cast NIL to keep lint happy (which is not so bad)
764  */
765 #define		NLNIL	( (struct nl *) NIL )
766 
767 /*
768  * Funny structures to use
769  * pointers in wild and wooly ways
770  */
771 struct {
772 	char	pchar;
773 };
774 struct {
775 	short	pint;
776 	short	pint2;
777 };
778 struct {
779 	long	plong;
780 };
781 struct {
782 	double	pdouble;
783 };
784 
785 #define	OCT	1
786 #define	HEX	2
787 
788 /*
789  * MAIN PROGRAM VARIABLES, MISCELLANY
790  */
791 
792 /*
793  * Variables forming a data base referencing
794  * the command line arguments with the "i" option, e.g.
795  * in "pi -i scanner.i compiler.p".
796  */
797 char	**pflist;
798 short	pflstc;
799 short	pfcnt;
800 
801 char	*filename;		/* current source file name */
802 long	tvec;
803 extern char	*snark;		/* SNARK */
804 extern char	*classes[ ];	/* maps namelist classes to string names */
805 
806 #define	derror error
807 
808 #ifdef	PC
809 
810     /*
811      *	the current function number, for [ lines
812      */
813     int	ftnno;
814 
815     /*
816      *	the pc output stream
817      */
818     FILE *pcstream;
819 
820 #endif PC
821