source: mainline/uspace/app/pcc/f77/fcom/misc.c@ c6a7b3a

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since c6a7b3a was a7de7182, checked in by Jiří Zárevúcky <zarevucky.jiri@…>, 14 years ago

Added pcc source tree (contents of pcc-1.0.0.tgz)

  • Property mode set to 100644
File size: 9.8 KB
Line 
1/* $Id: misc.c,v 1.17 2009/02/11 15:58:55 ragge Exp $ */
2/*
3 * Copyright(C) Caldera International Inc. 2001-2002. All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 *
9 * Redistributions of source code and documentation must retain the above
10 * copyright notice, this list of conditions and the following disclaimer.
11 * Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * All advertising materials mentioning features or use of this software
15 * must display the following acknowledgement:
16 * This product includes software developed or owned by Caldera
17 * International, Inc.
18 * Neither the name of Caldera International, Inc. nor the names of other
19 * contributors may be used to endorse or promote products derived from
20 * this software without specific prior written permission.
21 *
22 * USE OF THE SOFTWARE PROVIDED FOR UNDER THIS LICENSE BY CALDERA
23 * INTERNATIONAL, INC. AND CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR
24 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
25 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
26 * DISCLAIMED. IN NO EVENT SHALL CALDERA INTERNATIONAL, INC. BE LIABLE
27 * FOR ANY DIRECT, INDIRECT INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
28 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
29 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
30 * HOWEVER CAUSED AND ON ANY THEORY OFLIABILITY, WHETHER IN CONTRACT,
31 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
32 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
33 * POSSIBILITY OF SUCH DAMAGE.
34 */
35
36#include <string.h>
37
38#include "defines.h"
39#include "defs.h"
40
41int max(int, int);
42
43void
44cpn(n, a, b)
45register int n;
46register char *a, *b;
47{
48while(--n >= 0)
49 *b++ = *a++;
50}
51
52
53int
54eqn(n, a, b)
55register int n;
56register char *a, *b;
57{
58while(--n >= 0)
59 if(*a++ != *b++)
60 return(NO);
61return(YES);
62}
63
64
65
66
67
68
69int
70cmpstr(a, b, la, lb) /* compare two strings */
71register char *a, *b;
72ftnint la, lb;
73{
74register char *aend, *bend;
75aend = a + la;
76bend = b + lb;
77
78
79if(la <= lb)
80 {
81 while(a < aend)
82 if(*a != *b)
83 return( *a - *b );
84 else
85 { ++a; ++b; }
86
87 while(b < bend)
88 if(*b != ' ')
89 return(' ' - *b);
90 else
91 ++b;
92 }
93
94else
95 {
96 while(b < bend)
97 if(*a != *b)
98 return( *a - *b );
99 else
100 { ++a; ++b; }
101 while(a < aend)
102 if(*a != ' ')
103 return(*a - ' ');
104 else
105 ++a;
106 }
107return(0);
108}
109
110
111
112
113
114chainp hookup(x,y)
115register chainp x, y;
116{
117register chainp p;
118
119if(x == NULL)
120 return(y);
121
122for(p = x ; p->chain.nextp ; p = p->chain.nextp)
123 ;
124p->chain.nextp = y;
125return(x);
126}
127
128
129
130struct bigblock *mklist(p)
131chainp p;
132{
133register struct bigblock *q;
134
135q = BALLO();
136q->tag = TLIST;
137q->b_list.listp = p;
138return(q);
139}
140
141
142chainp
143mkchain(bigptr p, chainp q)
144{
145 chainp r;
146
147 if(chains) {
148 r = chains;
149 chains = chains->chain.nextp;
150 } else
151 r = ALLOC(chain);
152
153 r->chain.datap = p;
154 r->chain.nextp = q;
155 return(r);
156}
157
158
159
160char * varstr(n, s)
161register int n;
162register char *s;
163{
164register int i;
165static char name[XL+1];
166
167for(i=0; i<n && *s!=' ' && *s!='\0' ; ++i)
168 name[i] = *s++;
169
170name[i] = '\0';
171
172return( name );
173}
174
175
176
177
178char * varunder(n, s)
179register int n;
180register char *s;
181{
182register int i;
183static char name[XL+1];
184
185for(i=0; i<n && *s!=' ' && *s!='\0' ; ++i)
186 name[i] = *s++;
187
188name[i] = '\0';
189
190return( name );
191}
192
193
194
195
196
197char * nounder(n, s)
198register int n;
199register char *s;
200{
201register int i;
202static char name[XL+1];
203
204for(i=0; i<n && *s!=' ' && *s!='\0' ; ++s)
205 if(*s != '_')
206 name[i++] = *s;
207
208name[i] = '\0';
209
210return( name );
211}
212
213/*
214 * Save a block on heap.
215 */
216char *
217copyn(int n, char *s)
218{
219 char *p, *q;
220
221 p = q = ckalloc(n);
222 while(--n >= 0)
223 *q++ = *s++;
224 return(p);
225}
226
227/*
228 * Save a string on heap.
229 */
230char *
231copys(char *s)
232{
233 return(copyn(strlen(s)+1 , s));
234}
235
236/*
237 * convert a string to an int.
238 */
239ftnint
240convci(int n, char *s)
241{
242 ftnint sum;
243 sum = 0;
244 while(n-- > 0)
245 sum = 10*sum + (*s++ - '0');
246 return(sum);
247}
248
249char *convic(n)
250ftnint n;
251{
252static char s[20];
253register char *t;
254
255s[19] = '\0';
256t = s+19;
257
258do {
259 *--t = '0' + n%10;
260 n /= 10;
261 } while(n > 0);
262
263return(t);
264}
265
266
267
268double convcd(n, s)
269int n;
270register char *s;
271{
272char v[100];
273register char *t;
274if(n > 90)
275 {
276 err("too many digits in floating constant");
277 n = 90;
278 }
279for(t = v ; n-- > 0 ; s++)
280 *t++ = (*s=='d' ? 'e' : *s);
281*t = '\0';
282return( atof(v) );
283}
284
285
286
287struct bigblock *mkname(l, s)
288int l;
289register char *s;
290{
291struct hashentry *hp;
292int hash;
293register struct bigblock *q;
294register int i;
295char n[VL];
296
297hash = 0;
298for(i = 0 ; i<l && *s!='\0' ; ++i)
299 {
300 hash += *s;
301 n[i] = *s++;
302 }
303hash %= MAXHASH;
304while( i < VL )
305 n[i++] = ' ';
306
307hp = hashtab + hash;
308while((q = hp->varp))
309 if( hash==hp->hashval && eqn(VL,n,q->b_name.varname) )
310 return(q);
311 else if(++hp >= lasthash)
312 hp = hashtab;
313
314if(++nintnames >= MAXHASH-1)
315 fatal("hash table full");
316hp->varp = q = BALLO();
317hp->hashval = hash;
318q->tag = TNAME;
319cpn(VL, n, q->b_name.varname);
320return(q);
321}
322
323
324
325struct labelblock *mklabel(l)
326ftnint l;
327{
328register struct labelblock *lp;
329
330if(l == 0)
331 return(0);
332
333for(lp = labeltab ; lp < highlabtab ; ++lp)
334 if(lp->stateno == l)
335 return(lp);
336
337if(++highlabtab >= labtabend)
338 fatal("too many statement numbers");
339
340lp->stateno = l;
341lp->labelno = newlabel();
342lp->blklevel = 0;
343lp->labused = NO;
344lp->labdefined = NO;
345lp->labinacc = NO;
346lp->labtype = LABUNKNOWN;
347return(lp);
348}
349
350int
351newlabel()
352{
353return( lastlabno++ );
354}
355
356
357/* find or put a name in the external symbol table */
358
359struct extsym *mkext(s)
360char *s;
361{
362int i;
363register char *t;
364char n[XL];
365struct extsym *p;
366
367i = 0;
368t = n;
369while(i<XL && *s)
370 *t++ = *s++;
371while(t < n+XL)
372 *t++ = ' ';
373
374for(p = extsymtab ; p<nextext ; ++p)
375 if(eqn(XL, n, p->extname))
376 return( p );
377
378if(nextext >= lastext)
379 fatal("too many external symbols");
380
381cpn(XL, n, nextext->extname);
382nextext->extstg = STGUNKNOWN;
383nextext->extsave = NO;
384nextext->extp = 0;
385nextext->extleng = 0;
386nextext->maxleng = 0;
387nextext->extinit = NO;
388return( nextext++ );
389}
390
391
392
393
394
395
396
397
398struct bigblock *builtin(t, s)
399int t;
400char *s;
401{
402register struct extsym *p;
403register struct bigblock *q;
404
405p = mkext(s);
406if(p->extstg == STGUNKNOWN)
407 p->extstg = STGEXT;
408else if(p->extstg != STGEXT)
409 {
410 err1("improper use of builtin %s", s);
411 return(0);
412 }
413
414q = BALLO();
415q->tag = TADDR;
416q->vtype = t;
417q->vclass = CLPROC;
418q->vstg = STGEXT;
419q->b_addr.memno = p - extsymtab;
420return(q);
421}
422
423
424void
425frchain(p)
426register chainp *p;
427{
428register chainp q;
429
430if(p==0 || *p==0)
431 return;
432
433for(q = *p; q->chain.nextp ; q = q->chain.nextp)
434 ;
435q->chain.nextp = chains;
436chains = *p;
437*p = 0;
438}
439
440
441ptr cpblock(n,p)
442register int n;
443register void * p;
444{
445register char *q, *r = p;
446ptr q0;
447
448q = q0 = ckalloc(n);
449while(n-- > 0)
450 *q++ = *r++;
451return(q0);
452}
453
454
455int
456max(a,b)
457int a,b;
458{
459return( a>b ? a : b);
460}
461
462
463ftnint lmax(a, b)
464ftnint a, b;
465{
466return( a>b ? a : b);
467}
468
469ftnint lmin(a, b)
470ftnint a, b;
471{
472return(a < b ? a : b);
473}
474
475
476
477int
478maxtype(t1, t2)
479int t1, t2;
480{
481int t;
482
483t = max(t1, t2);
484if(t==TYCOMPLEX && (t1==TYDREAL || t2==TYDREAL) )
485 t = TYDCOMPLEX;
486return(t);
487}
488
489
490
491/* return log base 2 of n if n a power of 2; otherwise -1 */
492int
493flog2(n)
494ftnint n;
495{
496int k;
497
498/* trick based on binary representation */
499
500if(n<=0 || (n & (n-1))!=0)
501 return(-1);
502
503for(k = 0 ; n >>= 1 ; ++k)
504 ;
505return(k);
506}
507
508
509void
510frrpl()
511{
512chainp rp;
513
514while(rpllist)
515 {
516 rp = rpllist->rplblock.nextp;
517 ckfree(rpllist);
518 rpllist = rp;
519 }
520}
521
522void
523popstack(p)
524register chainp *p;
525{
526register chainp q;
527
528if(p==NULL || *p==NULL)
529 fatal("popstack: stack empty");
530q = (*p)->chain.nextp;
531ckfree(*p);
532*p = q;
533}
534
535
536
537struct bigblock *
538callk(type, name, args)
539int type;
540char *name;
541bigptr args;
542{
543register struct bigblock *p;
544
545p = mkexpr(OPCALL, builtin(type,name), args);
546p->vtype = type;
547return(p);
548}
549
550
551
552struct bigblock *
553call4(type, name, arg1, arg2, arg3, arg4)
554int type;
555char *name;
556bigptr arg1, arg2, arg3, arg4;
557{
558struct bigblock *args;
559args = mklist( mkchain(arg1, mkchain(arg2, mkchain(arg3, mkchain(arg4, NULL)) ) ) );
560return( callk(type, name, args) );
561}
562
563
564
565
566struct bigblock *call3(type, name, arg1, arg2, arg3)
567int type;
568char *name;
569bigptr arg1, arg2, arg3;
570{
571struct bigblock *args;
572args = mklist( mkchain(arg1, mkchain(arg2, mkchain(arg3, NULL) ) ) );
573return( callk(type, name, args) );
574}
575
576
577
578
579
580struct bigblock *
581call2(type, name, arg1, arg2)
582int type;
583char *name;
584bigptr arg1, arg2;
585{
586bigptr args;
587
588args = mklist( mkchain(arg1, mkchain(arg2, NULL) ) );
589return( callk(type,name, args) );
590}
591
592
593
594
595struct bigblock *call1(type, name, arg)
596int type;
597char *name;
598bigptr arg;
599{
600return( callk(type,name, mklist(mkchain(arg,0)) ));
601}
602
603
604struct bigblock *call0(type, name)
605int type;
606char *name;
607{
608return( callk(type, name, NULL) );
609}
610
611
612
613struct bigblock *
614mkiodo(dospec, list)
615chainp dospec, list;
616{
617register struct bigblock *q;
618
619q = BALLO();
620q->tag = TIMPLDO;
621q->b_impldo.varnp = (struct bigblock *)dospec;
622q->b_impldo.datalist = list;
623return(q);
624}
625
626
627
628
629ptr
630ckalloc(int n)
631{
632 ptr p;
633
634 if ((p = calloc(1, (unsigned) n)) == NULL)
635 fatal("out of memory");
636#ifdef PCC_DEBUG
637 if (mflag)
638 printf("ckalloc: sz %d ptr %p\n", n, p);
639#endif
640 return(p);
641}
642
643void
644ckfree(void *p)
645{
646#ifdef PCC_DEBUG
647 if (mflag)
648 printf("ckfree: ptr %p\n", p);
649#endif
650 free(p);
651}
652
653#if 0
654int
655isaddr(p)
656register bigptr p;
657{
658if(p->tag == TADDR)
659 return(YES);
660if(p->tag == TEXPR)
661 switch(p->b_expr.opcode)
662 {
663 case OPCOMMA:
664 return( isaddr(p->b_expr.rightp) );
665
666 case OPASSIGN:
667 case OPPLUSEQ:
668 return( isaddr(p->b_expr.leftp) );
669 }
670return(NO);
671}
672#endif
673
674/*
675 * Return YES if not an expression.
676 */
677int
678addressable(bigptr p)
679{
680 switch(p->tag) {
681 case TCONST:
682 return(YES);
683
684 case TADDR:
685 return( addressable(p->b_addr.memoffset) );
686
687 default:
688 return(NO);
689 }
690}
691
692
693int
694hextoi(c)
695register int c;
696{
697register char *p;
698static char p0[17] = "0123456789abcdef";
699
700for(p = p0 ; *p ; ++p)
701 if(*p == c)
702 return( p-p0 );
703return(16);
704}
Note: See TracBrowser for help on using the repository browser.