xref: /csrg-svn/usr.bin/f77/pass1.tahoe/conv.c (revision 47951)
1*47951Sbostic /*-
2*47951Sbostic  * Copyright (c) 1980 The Regents of the University of California.
3*47951Sbostic  * All rights reserved.
4*47951Sbostic  *
5*47951Sbostic  * %sccs.include.proprietary.c%
6*47951Sbostic  */
7*47951Sbostic 
8*47951Sbostic #ifndef lint
9*47951Sbostic static char sccsid[] = "@(#)conv.c	5.3 (Berkeley) 04/12/91";
10*47951Sbostic #endif /* not lint */
11*47951Sbostic 
1243203Sbostic #include "defs.h"
1343203Sbostic #include "conv.h"
1443203Sbostic 
1543203Sbostic int badvalue;
1643203Sbostic 
1743203Sbostic 
1843203Sbostic /*  The following constants are used to check the limits of  */
1943203Sbostic /*  conversions.  Dmaxword is the largest double precision   */
2043203Sbostic /*  number which can be converted to a two-byte integer      */
2143203Sbostic /*  without overflow.  Dminword is the smallest double       */
2243203Sbostic /*  precision value which can be converted to a two-byte     */
2343203Sbostic /*  integer without overflow.  Dmaxint and dminint are the   */
2443203Sbostic /*  analogous values for four-byte integers.                 */
2543203Sbostic 
2643203Sbostic /* short array should be correct for both VAX and TAHOE */
2743203Sbostic 
2843203Sbostic LOCAL short dmaxword[] = { 0x47ff, 0xfeff, 0xffff, 0xffff }; /* 32767.5 */
2943203Sbostic LOCAL short dminword[] = { 0xc800, 0x007f, 0xffff, 0xffff }; /* -32768.499999999999 */
3043203Sbostic 
3143203Sbostic LOCAL short dmaxint[]  = { 0x4fff, 0xffff, 0xfeff, 0xffff }; /* 2147483647.5 */
3243203Sbostic LOCAL short dminint[]  = { 0xd000, 0x0000, 0x007f, 0xffff }; /* -2147483648.4999999 */
3343203Sbostic 
3443203Sbostic LOCAL short dmaxreal[] = { 0x7fff, 0xffff, 0x7fff, 0xffff }; /* 1.7014117838986683e+38 */
3543203Sbostic LOCAL short dminreal[] = { 0xffff, 0xffff, 0x7fff, 0xffff }; /* -1.7014117838986683e+38 */
3643203Sbostic 
3743203Sbostic 
3843203Sbostic 
3943203Sbostic /*  The routines which follow are used to convert  */
4043203Sbostic /*  constants into constants of other types.       */
4143203Sbostic 
4243203Sbostic LOCAL char *
grabbits(len,cp)4343203Sbostic grabbits(len, cp)
4443203Sbostic int len;
4543203Sbostic Constp cp;
4643203Sbostic {
4743203Sbostic 
4843203Sbostic   static char *toobig = "bit value too large";
4943203Sbostic 
5043203Sbostic   register char *p;
5143203Sbostic   register char *bits;
5243203Sbostic   register int i;
5343203Sbostic   register int k;
5443203Sbostic   register int lenb;
5543203Sbostic 
5646301Sbostic   bits = cp->constant.ccp;
5746301Sbostic   lenb = cp->vleng->constblock.constant.ci;
5843203Sbostic 
5943203Sbostic   p = (char *) ckalloc(len);
6043203Sbostic 
6143203Sbostic   if (len >= lenb)
6243203Sbostic     k = lenb;
6343203Sbostic   else
6443203Sbostic     {
6543203Sbostic       k = len;
6643203Sbostic       if ( badvalue == 0 )
6743203Sbostic 	{
6843203Sbostic #if (HERE == PDP11 || HERE == VAX)
6943203Sbostic 	  i = len;
7043203Sbostic 	  while ( i < lenb && bits[i] == 0 )
7143203Sbostic 	    i++;
7243203Sbostic 	  if (i < lenb)
7343203Sbostic 	    badvalue = 1;
7443203Sbostic #else
7543203Sbostic 	  i = lenb - len - 1;
7643203Sbostic 	  while ( i >= 0 && bits[i] == 0)
7743203Sbostic 	    i--;
7843203Sbostic 	  if (i >= 0)
7943203Sbostic 	    badvalue = 1;
8043203Sbostic #endif
8143203Sbostic 	  if (badvalue)
8243203Sbostic 	    warn(toobig);
8343203Sbostic 	}
8443203Sbostic     }
8543203Sbostic 
8643203Sbostic #if (HERE == PDP11 || HERE == VAX)
8743203Sbostic   i = 0;
8843203Sbostic   while (i < k)
8943203Sbostic     {
9043203Sbostic       p[i] = bits[i];
9143203Sbostic       i++;
9243203Sbostic     }
9343203Sbostic #else
9443203Sbostic   i = lenb;
9543203Sbostic   while (k > 0)
9643203Sbostic     p[--k] = bits[--i];
9743203Sbostic #endif
9843203Sbostic 
9943203Sbostic   return (p);
10043203Sbostic }
10143203Sbostic 
10243203Sbostic 
10343203Sbostic 
10443203Sbostic LOCAL char *
grabbytes(len,cp)10543203Sbostic grabbytes(len, cp)
10643203Sbostic int len;
10743203Sbostic Constp cp;
10843203Sbostic {
10943203Sbostic   register char *p;
11043203Sbostic   register char *bytes;
11143203Sbostic   register int i;
11243203Sbostic   register int k;
11343203Sbostic   register int lenb;
11443203Sbostic 
11546301Sbostic   bytes = cp->constant.ccp;
11646301Sbostic   lenb = cp->vleng->constblock.constant.ci;
11743203Sbostic 
11843203Sbostic   p = (char *) ckalloc(len);
11943203Sbostic 
12043203Sbostic   if (len >= lenb)
12143203Sbostic     k = lenb;
12243203Sbostic   else
12343203Sbostic     k = len;
12443203Sbostic 
12543203Sbostic   i = 0;
12643203Sbostic   while (i < k)
12743203Sbostic     {
12843203Sbostic       p[i] = bytes[i];
12943203Sbostic       i++;
13043203Sbostic     }
13143203Sbostic 
13243203Sbostic   while (i < len)
13343203Sbostic     p[i++] = BLANK;
13443203Sbostic 
13543203Sbostic   return (p);
13643203Sbostic }
13743203Sbostic 
13843203Sbostic 
13943203Sbostic 
14043203Sbostic LOCAL expptr
cshort(cp)14143203Sbostic cshort(cp)
14243203Sbostic Constp cp;
14343203Sbostic {
14443203Sbostic   static char *toobig = "data value too large";
14543203Sbostic   static char *reserved = "reserved operand assigned to an integer";
14643203Sbostic   static char *compat1 = "logical datum assigned to an integer variable";
14743203Sbostic   static char *compat2 = "character datum assigned to an integer variable";
14843203Sbostic 
14943203Sbostic   register expptr p;
15043203Sbostic   register short *shortp;
15143203Sbostic   register ftnint value;
15243203Sbostic   register long *rp;
15343203Sbostic   register double *minp;
15443203Sbostic   register double *maxp;
15543203Sbostic   realvalue x;
15643203Sbostic 
15743203Sbostic   switch (cp->vtype)
15843203Sbostic     {
15943203Sbostic     case TYBITSTR:
16043203Sbostic       shortp = (short *) grabbits(2, cp);
16143203Sbostic       p = (expptr) mkconst(TYSHORT);
16246301Sbostic       p->constblock.constant.ci = *shortp;
16343203Sbostic       free((char *) shortp);
16443203Sbostic       break;
16543203Sbostic 
16643203Sbostic     case TYSHORT:
16743203Sbostic       p = (expptr) cpexpr(cp);
16843203Sbostic       break;
16943203Sbostic 
17043203Sbostic     case TYLONG:
17146301Sbostic       value = cp->constant.ci;
17243203Sbostic       if (value >= MINWORD && value <= MAXWORD)
17343203Sbostic 	{
17443203Sbostic 	  p = (expptr) mkconst(TYSHORT);
17546301Sbostic 	  p->constblock.constant.ci = value;
17643203Sbostic 	}
17743203Sbostic       else
17843203Sbostic 	{
17943203Sbostic 	  if (badvalue <= 1)
18043203Sbostic 	    {
18143203Sbostic 	      badvalue = 2;
18243203Sbostic 	      err(toobig);
18343203Sbostic 	    }
18443203Sbostic 	  p = errnode();
18543203Sbostic 	}
18643203Sbostic       break;
18743203Sbostic 
18843203Sbostic     case TYREAL:
18943203Sbostic     case TYDREAL:
19043203Sbostic     case TYCOMPLEX:
19143203Sbostic     case TYDCOMPLEX:
19243203Sbostic       minp = (double *) dminword;
19343203Sbostic       maxp = (double *) dmaxword;
19446301Sbostic       rp = (long *) &(cp->constant.cd[0]);
19543203Sbostic       x.q.word1 = rp[0];
19643203Sbostic       x.q.word2 = rp[1];
19743203Sbostic       if (x.f.sign == 1 && x.f.exp == 0)
19843203Sbostic 	{
19943203Sbostic 	  if (badvalue <= 1)
20043203Sbostic 	    {
20143203Sbostic 	      badvalue = 2;
20243203Sbostic 	      err(reserved);
20343203Sbostic 	    }
20443203Sbostic 	  p = errnode();
20543203Sbostic 	}
20643203Sbostic       else if (x.d >= *minp && x.d <= *maxp)
20743203Sbostic 	{
20843203Sbostic 	  p = (expptr) mkconst(TYSHORT);
20946301Sbostic 	  p->constblock.constant.ci = x.d;
21043203Sbostic 	}
21143203Sbostic       else
21243203Sbostic 	{
21343203Sbostic 	  if (badvalue <= 1)
21443203Sbostic 	    {
21543203Sbostic 	      badvalue = 2;
21643203Sbostic 	      err(toobig);
21743203Sbostic 	    }
21843203Sbostic 	  p = errnode();
21943203Sbostic 	}
22043203Sbostic       break;
22143203Sbostic 
22243203Sbostic     case TYLOGICAL:
22343203Sbostic       if (badvalue <= 1)
22443203Sbostic 	{
22543203Sbostic 	  badvalue = 2;
22643203Sbostic 	  err(compat1);
22743203Sbostic 	}
22843203Sbostic       p = errnode();
22943203Sbostic       break;
23043203Sbostic 
23143203Sbostic     case TYCHAR:
23243203Sbostic       if ( !ftn66flag && badvalue == 0 )
23343203Sbostic 	{
23443203Sbostic 	  badvalue = 1;
23543203Sbostic 	  warn(compat2);
23643203Sbostic 	}
23743203Sbostic 
23843203Sbostic     case TYHOLLERITH:
23943203Sbostic       shortp = (short *) grabbytes(2, cp);
24043203Sbostic       p = (expptr) mkconst(TYSHORT);
24146301Sbostic       p->constblock.constant.ci = *shortp;
24243203Sbostic       free((char *) shortp);
24343203Sbostic       break;
24443203Sbostic 
24543203Sbostic     case TYERROR:
24643203Sbostic       p = errnode();
24743203Sbostic       break;
24843203Sbostic     }
24943203Sbostic 
25043203Sbostic   return (p);
25143203Sbostic }
25243203Sbostic 
25343203Sbostic 
25443203Sbostic 
25543203Sbostic LOCAL expptr
clong(cp)25643203Sbostic clong(cp)
25743203Sbostic Constp cp;
25843203Sbostic {
25943203Sbostic   static char *toobig = "data value too large";
26043203Sbostic   static char *reserved = "reserved operand assigned to an integer";
26143203Sbostic   static char *compat1 = "logical datum assigned to an integer variable";
26243203Sbostic   static char *compat2 = "character datum assigned to an integer variable";
26343203Sbostic 
26443203Sbostic   register expptr p;
26543203Sbostic   register ftnint *longp;
26643203Sbostic   register long *rp;
26743203Sbostic   register double *minp;
26843203Sbostic   register double *maxp;
26943203Sbostic   realvalue x;
27043203Sbostic 
27143203Sbostic   switch (cp->vtype)
27243203Sbostic     {
27343203Sbostic     case TYBITSTR:
27443203Sbostic       longp = (ftnint *) grabbits(4, cp);
27543203Sbostic       p = (expptr) mkconst(TYLONG);
27646301Sbostic       p->constblock.constant.ci = *longp;
27743203Sbostic       free((char *) longp);
27843203Sbostic       break;
27943203Sbostic 
28043203Sbostic     case TYSHORT:
28143203Sbostic       p = (expptr) mkconst(TYLONG);
28246301Sbostic       p->constblock.constant.ci = cp->constant.ci;
28343203Sbostic       break;
28443203Sbostic 
28543203Sbostic     case TYLONG:
28643203Sbostic       p = (expptr) cpexpr(cp);
28743203Sbostic       break;
28843203Sbostic 
28943203Sbostic     case TYREAL:
29043203Sbostic     case TYDREAL:
29143203Sbostic     case TYCOMPLEX:
29243203Sbostic     case TYDCOMPLEX:
29343203Sbostic       minp = (double *) dminint;
29443203Sbostic       maxp = (double *) dmaxint;
29546301Sbostic       rp = (long *) &(cp->constant.cd[0]);
29643203Sbostic       x.q.word1 = rp[0];
29743203Sbostic       x.q.word2 = rp[1];
29843203Sbostic       if (x.f.sign == 1 && x.f.exp == 0)
29943203Sbostic 	{
30043203Sbostic 	  if (badvalue <= 1)
30143203Sbostic 	    {
30243203Sbostic 	      badvalue = 2;
30343203Sbostic 	      err(reserved);
30443203Sbostic 	    }
30543203Sbostic 	  p = errnode();
30643203Sbostic 	}
30743203Sbostic       else if (x.d >= *minp && x.d <= *maxp)
30843203Sbostic 	{
30943203Sbostic 	  p = (expptr) mkconst(TYLONG);
31046301Sbostic 	  p->constblock.constant.ci = x.d;
31143203Sbostic 	}
31243203Sbostic       else
31343203Sbostic 	{
31443203Sbostic 	  if (badvalue <= 1)
31543203Sbostic 	    {
31643203Sbostic 	      badvalue = 2;
31743203Sbostic 	      err(toobig);
31843203Sbostic 	    }
31943203Sbostic 	  p = errnode();
32043203Sbostic 	}
32143203Sbostic       break;
32243203Sbostic 
32343203Sbostic     case TYLOGICAL:
32443203Sbostic       if (badvalue <= 1)
32543203Sbostic 	{
32643203Sbostic 	  badvalue = 2;
32743203Sbostic 	  err(compat1);
32843203Sbostic 	}
32943203Sbostic       p = errnode();
33043203Sbostic       break;
33143203Sbostic 
33243203Sbostic     case TYCHAR:
33343203Sbostic       if ( !ftn66flag && badvalue == 0 )
33443203Sbostic 	{
33543203Sbostic 	  badvalue = 1;
33643203Sbostic 	  warn(compat2);
33743203Sbostic 	}
33843203Sbostic 
33943203Sbostic     case TYHOLLERITH:
34043203Sbostic       longp = (ftnint *) grabbytes(4, cp);
34143203Sbostic       p = (expptr) mkconst(TYLONG);
34246301Sbostic       p->constblock.constant.ci = *longp;
34343203Sbostic       free((char *) longp);
34443203Sbostic       break;
34543203Sbostic 
34643203Sbostic     case TYERROR:
34743203Sbostic       p = errnode();
34843203Sbostic       break;
34943203Sbostic     }
35043203Sbostic 
35143203Sbostic   return (p);
35243203Sbostic }
35343203Sbostic 
35443203Sbostic 
35543203Sbostic 
35643203Sbostic LOCAL expptr
creal(cp)35743203Sbostic creal(cp)
35843203Sbostic Constp cp;
35943203Sbostic {
36043203Sbostic   static char *toobig = "data value too large";
36143203Sbostic   static char *compat1 = "logical datum assigned to a real variable";
36243203Sbostic   static char *compat2 = "character datum assigned to a real variable";
36343203Sbostic 
36443203Sbostic   register expptr p;
36543203Sbostic   register long *longp;
36643203Sbostic   register long *rp;
36743203Sbostic   register double *minp;
36843203Sbostic   register double *maxp;
36943203Sbostic   realvalue x;
37043203Sbostic   float y;
37143203Sbostic 
37243203Sbostic   switch (cp->vtype)
37343203Sbostic     {
37443203Sbostic     case TYBITSTR:
37543203Sbostic       longp = (long *) grabbits(4, cp);
37643203Sbostic       p = (expptr) mkconst(TYREAL);
37746301Sbostic       rp = (long *) &(p->constblock.constant.cd[0]);
37843203Sbostic       rp[0] = *longp;
37943203Sbostic       free((char *) longp);
38043203Sbostic       break;
38143203Sbostic 
38243203Sbostic     case TYSHORT:
38343203Sbostic     case TYLONG:
38443203Sbostic       p = (expptr) mkconst(TYREAL);
38546301Sbostic       p->constblock.constant.cd[0] = cp->constant.ci;
38643203Sbostic       break;
38743203Sbostic 
38843203Sbostic     case TYREAL:
38943203Sbostic     case TYDREAL:
39043203Sbostic     case TYCOMPLEX:
39143203Sbostic     case TYDCOMPLEX:
39243203Sbostic       minp = (double *) dminreal;
39343203Sbostic       maxp = (double *) dmaxreal;
39446301Sbostic       rp = (long *) &(cp->constant.cd[0]);
39543203Sbostic       x.q.word1 = rp[0];
39643203Sbostic       x.q.word2 = rp[1];
39743203Sbostic       if (x.f.sign == 1 && x.f.exp == 0)
39843203Sbostic 	{
39943203Sbostic 	  p = (expptr) mkconst(TYREAL);
40046301Sbostic 	  rp = (long *) &(p->constblock.constant.cd[0]);
40143203Sbostic 	  rp[0] = x.q.word1;
40243203Sbostic 	}
40343203Sbostic       else if (x.d >= *minp && x.d <= *maxp)
40443203Sbostic 	{
40543203Sbostic 	  p = (expptr) mkconst(TYREAL);
40643203Sbostic 	  y = x.d;
40746301Sbostic 	  p->constblock.constant.cd[0] = y;
40843203Sbostic 	}
40943203Sbostic       else
41043203Sbostic 	{
41143203Sbostic 	  if (badvalue <= 1)
41243203Sbostic 	    {
41343203Sbostic 	      badvalue = 2;
41443203Sbostic 	      err(toobig);
41543203Sbostic 	    }
41643203Sbostic 	  p = errnode();
41743203Sbostic 	}
41843203Sbostic       break;
41943203Sbostic 
42043203Sbostic     case TYLOGICAL:
42143203Sbostic       if (badvalue <= 1)
42243203Sbostic 	{
42343203Sbostic 	  badvalue = 2;
42443203Sbostic 	  err(compat1);
42543203Sbostic 	}
42643203Sbostic       p = errnode();
42743203Sbostic       break;
42843203Sbostic 
42943203Sbostic     case TYCHAR:
43043203Sbostic       if ( !ftn66flag && badvalue == 0)
43143203Sbostic 	{
43243203Sbostic 	  badvalue = 1;
43343203Sbostic 	  warn(compat2);
43443203Sbostic 	}
43543203Sbostic 
43643203Sbostic     case TYHOLLERITH:
43743203Sbostic       longp = (long *) grabbytes(4, cp);
43843203Sbostic       p = (expptr) mkconst(TYREAL);
43946301Sbostic       rp = (long *) &(p->constblock.constant.cd[0]);
44043203Sbostic       rp[0] = *longp;
44143203Sbostic       free((char *) longp);
44243203Sbostic       break;
44343203Sbostic 
44443203Sbostic     case TYERROR:
44543203Sbostic       p = errnode();
44643203Sbostic       break;
44743203Sbostic     }
44843203Sbostic 
44943203Sbostic   return (p);
45043203Sbostic }
45143203Sbostic 
45243203Sbostic 
45343203Sbostic 
45443203Sbostic LOCAL expptr
cdreal(cp)45543203Sbostic cdreal(cp)
45643203Sbostic Constp cp;
45743203Sbostic {
45843203Sbostic   static char *compat1 =
45943203Sbostic 	"logical datum assigned to a double precision variable";
46043203Sbostic   static char *compat2 =
46143203Sbostic 	"character datum assigned to a double precision variable";
46243203Sbostic 
46343203Sbostic   register expptr p;
46443203Sbostic   register long *longp;
46543203Sbostic   register long *rp;
46643203Sbostic 
46743203Sbostic   switch (cp->vtype)
46843203Sbostic     {
46943203Sbostic     case TYBITSTR:
47043203Sbostic       longp = (long *) grabbits(8, cp);
47143203Sbostic       p = (expptr) mkconst(TYDREAL);
47246301Sbostic       rp = (long *) &(p->constblock.constant.cd[0]);
47343203Sbostic       rp[0] = longp[0];
47443203Sbostic       rp[1] = longp[1];
47543203Sbostic       free((char *) longp);
47643203Sbostic       break;
47743203Sbostic 
47843203Sbostic     case TYSHORT:
47943203Sbostic     case TYLONG:
48043203Sbostic       p = (expptr) mkconst(TYDREAL);
48146301Sbostic       p->constblock.constant.cd[0] = cp->constant.ci;
48243203Sbostic       break;
48343203Sbostic 
48443203Sbostic     case TYREAL:
48543203Sbostic     case TYDREAL:
48643203Sbostic     case TYCOMPLEX:
48743203Sbostic     case TYDCOMPLEX:
48843203Sbostic       p = (expptr) mkconst(TYDREAL);
48946301Sbostic       longp = (long *) &(cp->constant.cd[0]);
49046301Sbostic       rp = (long *) &(p->constblock.constant.cd[0]);
49143203Sbostic       rp[0] = longp[0];
49243203Sbostic       rp[1] = longp[1];
49343203Sbostic       break;
49443203Sbostic 
49543203Sbostic     case TYLOGICAL:
49643203Sbostic       if (badvalue <= 1)
49743203Sbostic 	{
49843203Sbostic 	  badvalue = 2;
49943203Sbostic 	  err(compat1);
50043203Sbostic 	}
50143203Sbostic       p = errnode();
50243203Sbostic       break;
50343203Sbostic 
50443203Sbostic     case TYCHAR:
50543203Sbostic       if ( !ftn66flag && badvalue == 0 )
50643203Sbostic 	{
50743203Sbostic 	  badvalue = 1;
50843203Sbostic 	  warn(compat2);
50943203Sbostic 	}
51043203Sbostic 
51143203Sbostic     case TYHOLLERITH:
51243203Sbostic       longp = (long *) grabbytes(8, cp);
51343203Sbostic       p = (expptr) mkconst(TYDREAL);
51446301Sbostic       rp = (long *) &(p->constblock.constant.cd[0]);
51543203Sbostic       rp[0] = longp[0];
51643203Sbostic       rp[1] = longp[1];
51743203Sbostic       free((char *) longp);
51843203Sbostic       break;
51943203Sbostic 
52043203Sbostic     case TYERROR:
52143203Sbostic       p = errnode();
52243203Sbostic       break;
52343203Sbostic     }
52443203Sbostic 
52543203Sbostic   return (p);
52643203Sbostic }
52743203Sbostic 
52843203Sbostic 
52943203Sbostic 
53043203Sbostic LOCAL expptr
ccomplex(cp)53143203Sbostic ccomplex(cp)
53243203Sbostic Constp cp;
53343203Sbostic {
53443203Sbostic   static char *toobig = "data value too large";
53543203Sbostic   static char *compat1 = "logical datum assigned to a complex variable";
53643203Sbostic   static char *compat2 = "character datum assigned to a complex variable";
53743203Sbostic 
53843203Sbostic   register expptr p;
53943203Sbostic   register long *longp;
54043203Sbostic   register long *rp;
54143203Sbostic   register double *minp;
54243203Sbostic   register double *maxp;
54343203Sbostic   realvalue re, im;
54443203Sbostic   int overflow;
54543203Sbostic   float x;
54643203Sbostic 
54743203Sbostic   switch (cp->vtype)
54843203Sbostic     {
54943203Sbostic     case TYBITSTR:
55043203Sbostic       longp = (long *) grabbits(8, cp);
55143203Sbostic       p = (expptr) mkconst(TYCOMPLEX);
55246301Sbostic       rp = (long *) &(p->constblock.constant.cd[0]);
55343203Sbostic       rp[0] = longp[0];
55443203Sbostic       rp[2] = longp[1];
55543203Sbostic       free((char *) longp);
55643203Sbostic       break;
55743203Sbostic 
55843203Sbostic     case TYSHORT:
55943203Sbostic     case TYLONG:
56043203Sbostic       p = (expptr) mkconst(TYCOMPLEX);
56146301Sbostic       p->constblock.constant.cd[0] = cp->constant.ci;
56243203Sbostic       break;
56343203Sbostic 
56443203Sbostic     case TYREAL:
56543203Sbostic     case TYDREAL:
56643203Sbostic     case TYCOMPLEX:
56743203Sbostic     case TYDCOMPLEX:
56843203Sbostic       overflow = 0;
56943203Sbostic       minp = (double *) dminreal;
57043203Sbostic       maxp = (double *) dmaxreal;
57146301Sbostic       rp = (long *) &(cp->constant.cd[0]);
57243203Sbostic       re.q.word1 = rp[0];
57343203Sbostic       re.q.word2 = rp[1];
57443203Sbostic       im.q.word1 = rp[2];
57543203Sbostic       im.q.word2 = rp[3];
57643203Sbostic       if (((re.f.sign == 0 || re.f.exp != 0) &&
57743203Sbostic 	   (re.d < *minp || re.d > *maxp))       ||
57843203Sbostic 	  ((im.f.sign == 0 || re.f.exp != 0) &&
57943203Sbostic 	   (im.d < *minp || re.d > *maxp)))
58043203Sbostic 	{
58143203Sbostic 	  if (badvalue <= 1)
58243203Sbostic 	    {
58343203Sbostic 	      badvalue = 2;
58443203Sbostic 	      err(toobig);
58543203Sbostic 	    }
58643203Sbostic 	  p = errnode();
58743203Sbostic 	}
58843203Sbostic       else
58943203Sbostic 	{
59043203Sbostic 	  p = (expptr) mkconst(TYCOMPLEX);
59143203Sbostic 	  if (re.f.sign == 1 && re.f.exp == 0)
59243203Sbostic 	    re.q.word2 = 0;
59343203Sbostic 	  else
59443203Sbostic 	    {
59543203Sbostic 	      x = re.d;
59643203Sbostic 	      re.d = x;
59743203Sbostic 	    }
59843203Sbostic 	  if (im.f.sign == 1 && im.f.exp == 0)
59943203Sbostic 	    im.q.word2 = 0;
60043203Sbostic 	  else
60143203Sbostic 	    {
60243203Sbostic 	      x = im.d;
60343203Sbostic 	      im.d = x;
60443203Sbostic 	    }
60546301Sbostic 	  rp = (long *) &(p->constblock.constant.cd[0]);
60643203Sbostic 	  rp[0] = re.q.word1;
60743203Sbostic 	  rp[1] = re.q.word2;
60843203Sbostic 	  rp[2] = im.q.word1;
60943203Sbostic 	  rp[3] = im.q.word2;
61043203Sbostic 	}
61143203Sbostic       break;
61243203Sbostic 
61343203Sbostic     case TYLOGICAL:
61443203Sbostic       if (badvalue <= 1)
61543203Sbostic 	{
61643203Sbostic 	  badvalue = 2;
61743203Sbostic 	  err(compat1);
61843203Sbostic 	}
61943203Sbostic       break;
62043203Sbostic 
62143203Sbostic     case TYCHAR:
62243203Sbostic       if ( !ftn66flag && badvalue == 0)
62343203Sbostic 	{
62443203Sbostic 	  badvalue = 1;
62543203Sbostic 	  warn(compat2);
62643203Sbostic 	}
62743203Sbostic 
62843203Sbostic     case TYHOLLERITH:
62943203Sbostic       longp = (long *) grabbytes(8, cp);
63043203Sbostic       p = (expptr) mkconst(TYCOMPLEX);
63146301Sbostic       rp = (long *) &(p->constblock.constant.cd[0]);
63243203Sbostic       rp[0] = longp[0];
63343203Sbostic       rp[2] = longp[1];
63443203Sbostic       free((char *) longp);
63543203Sbostic       break;
63643203Sbostic 
63743203Sbostic     case TYERROR:
63843203Sbostic       p = errnode();
63943203Sbostic       break;
64043203Sbostic     }
64143203Sbostic 
64243203Sbostic   return (p);
64343203Sbostic }
64443203Sbostic 
64543203Sbostic 
64643203Sbostic 
64743203Sbostic LOCAL expptr
cdcomplex(cp)64843203Sbostic cdcomplex(cp)
64943203Sbostic Constp cp;
65043203Sbostic {
65143203Sbostic   static char *compat1 = "logical datum assigned to a complex variable";
65243203Sbostic   static char *compat2 = "character datum assigned to a complex variable";
65343203Sbostic 
65443203Sbostic   register expptr p;
65543203Sbostic   register long *longp;
65643203Sbostic   register long *rp;
65743203Sbostic 
65843203Sbostic   switch (cp->vtype)
65943203Sbostic     {
66043203Sbostic     case TYBITSTR:
66143203Sbostic       longp = (long *) grabbits(16, cp);
66243203Sbostic       p = (expptr) mkconst(TYDCOMPLEX);
66346301Sbostic       rp = (long *) &(p->constblock.constant.cd[0]);
66443203Sbostic       rp[0] = longp[0];
66543203Sbostic       rp[1] = longp[1];
66643203Sbostic       rp[2] = longp[2];
66743203Sbostic       rp[3] = longp[3];
66843203Sbostic       free((char *) longp);
66943203Sbostic       break;
67043203Sbostic 
67143203Sbostic     case TYSHORT:
67243203Sbostic     case TYLONG:
67343203Sbostic       p = (expptr) mkconst(TYDCOMPLEX);
67446301Sbostic       p->constblock.constant.cd[0] = cp->constant.ci;
67543203Sbostic       break;
67643203Sbostic 
67743203Sbostic     case TYREAL:
67843203Sbostic     case TYDREAL:
67943203Sbostic     case TYCOMPLEX:
68043203Sbostic     case TYDCOMPLEX:
68143203Sbostic       p = (expptr) mkconst(TYDCOMPLEX);
68246301Sbostic       longp = (long *) &(cp->constant.cd[0]);
68346301Sbostic       rp = (long *) &(p->constblock.constant.cd[0]);
68443203Sbostic       rp[0] = longp[0];
68543203Sbostic       rp[1] = longp[1];
68643203Sbostic       rp[2] = longp[2];
68743203Sbostic       rp[3] = longp[3];
68843203Sbostic       break;
68943203Sbostic 
69043203Sbostic     case TYLOGICAL:
69143203Sbostic       if (badvalue <= 1)
69243203Sbostic 	{
69343203Sbostic 	  badvalue = 2;
69443203Sbostic 	  err(compat1);
69543203Sbostic 	}
69643203Sbostic       p = errnode();
69743203Sbostic       break;
69843203Sbostic 
69943203Sbostic     case TYCHAR:
70043203Sbostic       if ( !ftn66flag && badvalue == 0 )
70143203Sbostic 	{
70243203Sbostic 	  badvalue = 1;
70343203Sbostic 	  warn(compat2);
70443203Sbostic 	}
70543203Sbostic 
70643203Sbostic     case TYHOLLERITH:
70743203Sbostic       longp = (long *) grabbytes(16, cp);
70843203Sbostic       p = (expptr) mkconst(TYDCOMPLEX);
70946301Sbostic       rp = (long *) &(p->constblock.constant.cd[0]);
71043203Sbostic       rp[0] = longp[0];
71143203Sbostic       rp[1] = longp[1];
71243203Sbostic       rp[2] = longp[2];
71343203Sbostic       rp[3] = longp[3];
71443203Sbostic       free((char *) longp);
71543203Sbostic       break;
71643203Sbostic 
71743203Sbostic     case TYERROR:
71843203Sbostic       p = errnode();
71943203Sbostic       break;
72043203Sbostic     }
72143203Sbostic 
72243203Sbostic   return (p);
72343203Sbostic }
72443203Sbostic 
72543203Sbostic 
72643203Sbostic 
72743203Sbostic LOCAL expptr
clogical(cp)72843203Sbostic clogical(cp)
72943203Sbostic Constp cp;
73043203Sbostic {
73143203Sbostic   static char *compat1 = "numeric datum assigned to a logical variable";
73243203Sbostic   static char *compat2 = "character datum assigned to a logical variable";
73343203Sbostic 
73443203Sbostic   register expptr p;
73543203Sbostic   register long *longp;
73643203Sbostic   register short *shortp;
73743203Sbostic   register int size;
73843203Sbostic 
73943203Sbostic   size = typesize[tylogical];
74043203Sbostic 
74143203Sbostic   switch (cp->vtype)
74243203Sbostic     {
74343203Sbostic     case TYBITSTR:
74443203Sbostic       p = (expptr) mkconst(tylogical);
74543203Sbostic       if (tylogical == TYSHORT)
74643203Sbostic 	{
74743203Sbostic 	  shortp = (short *) grabbits(size, cp);
74846301Sbostic 	  p->constblock.constant.ci = (int) *shortp;
74943203Sbostic 	  free((char *) shortp);
75043203Sbostic 	}
75143203Sbostic       else
75243203Sbostic 	{
75343203Sbostic 	  longp = (long *) grabbits(size, cp);
75446301Sbostic 	  p->constblock.constant.ci = *longp;
75543203Sbostic 	  free((char *) longp);
75643203Sbostic 	}
75743203Sbostic       break;
75843203Sbostic 
75943203Sbostic     case TYSHORT:
76043203Sbostic     case TYLONG:
76143203Sbostic     case TYREAL:
76243203Sbostic     case TYDREAL:
76343203Sbostic     case TYCOMPLEX:
76443203Sbostic     case TYDCOMPLEX:
76543203Sbostic       if (badvalue <= 1)
76643203Sbostic 	{
76743203Sbostic 	  badvalue = 2;
76843203Sbostic 	  err(compat1);
76943203Sbostic 	}
77043203Sbostic       p = errnode();
77143203Sbostic       break;
77243203Sbostic 
77343203Sbostic     case TYLOGICAL:
77443203Sbostic       p = (expptr) cpexpr(cp);
77543203Sbostic       p->constblock.vtype = tylogical;
77643203Sbostic       break;
77743203Sbostic 
77843203Sbostic     case TYCHAR:
77943203Sbostic       if ( !ftn66flag && badvalue == 0 )
78043203Sbostic 	{
78143203Sbostic 	  badvalue = 1;
78243203Sbostic 	  warn(compat2);
78343203Sbostic 	}
78443203Sbostic 
78543203Sbostic     case TYHOLLERITH:
78643203Sbostic       p = (expptr) mkconst(tylogical);
78743203Sbostic       if (tylogical == TYSHORT)
78843203Sbostic 	{
78943203Sbostic 	  shortp = (short *) grabbytes(size, cp);
79046301Sbostic 	  p->constblock.constant.ci = (int) *shortp;
79143203Sbostic 	  free((char *) shortp);
79243203Sbostic 	}
79343203Sbostic       else
79443203Sbostic 	{
79543203Sbostic 	  longp = (long *) grabbytes(4, cp);
79646301Sbostic 	  p->constblock.constant.ci = *longp;
79743203Sbostic 	  free((char *) longp);
79843203Sbostic 	}
79943203Sbostic       break;
80043203Sbostic 
80143203Sbostic     case TYERROR:
80243203Sbostic       p = errnode();
80343203Sbostic       break;
80443203Sbostic     }
80543203Sbostic 
80643203Sbostic   return (p);
80743203Sbostic }
80843203Sbostic 
80943203Sbostic 
81043203Sbostic 
81143203Sbostic LOCAL expptr
cchar(len,cp)81243203Sbostic cchar(len, cp)
81343203Sbostic int len;
81443203Sbostic Constp cp;
81543203Sbostic {
81643203Sbostic   static char *compat1 = "numeric datum assigned to a character variable";
81743203Sbostic   static char *compat2 = "logical datum assigned to a character variable";
81843203Sbostic 
81943203Sbostic   register expptr p;
82043203Sbostic   register char *value;
82143203Sbostic 
82243203Sbostic   switch (cp->vtype)
82343203Sbostic     {
82443203Sbostic     case TYBITSTR:
82543203Sbostic       value = grabbits(len, cp);
82643203Sbostic       p = (expptr) mkstrcon(len, value);
82743203Sbostic       free(value);
82843203Sbostic       break;
82943203Sbostic 
83043203Sbostic     case TYSHORT:
83143203Sbostic     case TYLONG:
83243203Sbostic     case TYREAL:
83343203Sbostic     case TYDREAL:
83443203Sbostic     case TYCOMPLEX:
83543203Sbostic     case TYDCOMPLEX:
83643203Sbostic       if (badvalue <= 1)
83743203Sbostic 	{
83843203Sbostic 	  badvalue = 2;
83943203Sbostic 	  err(compat1);
84043203Sbostic 	}
84143203Sbostic       p = errnode();
84243203Sbostic       break;
84343203Sbostic 
84443203Sbostic     case TYLOGICAL:
84543203Sbostic       if (badvalue <= 1)
84643203Sbostic 	{
84743203Sbostic 	  badvalue = 2;
84843203Sbostic 	  err(compat2);
84943203Sbostic 	}
85043203Sbostic       p = errnode();
85143203Sbostic       break;
85243203Sbostic 
85343203Sbostic     case TYCHAR:
85443203Sbostic     case TYHOLLERITH:
85543203Sbostic       value = grabbytes(len, cp);
85643203Sbostic       p = (expptr) mkstrcon(len, value);
85743203Sbostic       free(value);
85843203Sbostic       break;
85943203Sbostic 
86043203Sbostic     case TYERROR:
86143203Sbostic       p = errnode();
86243203Sbostic       break;
86343203Sbostic     }
86443203Sbostic 
86543203Sbostic   return (p);
86643203Sbostic }
86743203Sbostic 
86843203Sbostic 
86943203Sbostic 
87043203Sbostic expptr
convconst(type,len,constant)87146301Sbostic convconst(type, len, constant)
87243203Sbostic int type;
87343203Sbostic int len;
87446301Sbostic Constp constant;
87543203Sbostic {
87643203Sbostic   register expptr p;
87743203Sbostic 
87843203Sbostic   switch (type)
87943203Sbostic     {
88043203Sbostic     case TYSHORT:
88146301Sbostic       p = cshort(constant);
88243203Sbostic       break;
88343203Sbostic 
88443203Sbostic     case TYLONG:
88546301Sbostic       p = clong(constant);
88643203Sbostic       break;
88743203Sbostic 
88843203Sbostic     case TYREAL:
88946301Sbostic       p = creal(constant);
89043203Sbostic       break;
89143203Sbostic 
89243203Sbostic     case TYDREAL:
89346301Sbostic       p = cdreal(constant);
89443203Sbostic       break;
89543203Sbostic 
89643203Sbostic     case TYCOMPLEX:
89746301Sbostic       p = ccomplex(constant);
89843203Sbostic       break;
89943203Sbostic 
90043203Sbostic     case TYDCOMPLEX:
90146301Sbostic       p = cdcomplex(constant);
90243203Sbostic       break;
90343203Sbostic 
90443203Sbostic     case TYLOGICAL:
90546301Sbostic       p = clogical(constant);
90643203Sbostic       break;
90743203Sbostic 
90843203Sbostic     case TYCHAR:
90946301Sbostic       p = cchar(len, constant);
91043203Sbostic       break;
91143203Sbostic 
91243203Sbostic     case TYERROR:
91343203Sbostic     case TYUNKNOWN:
91443203Sbostic       p = errnode();
91543203Sbostic       break;
91643203Sbostic 
91743203Sbostic     default:
91843203Sbostic       badtype("convconst", type);
91943203Sbostic     }
92043203Sbostic 
92143203Sbostic   return (p);
92243203Sbostic }
923