Exemple #1
0
void
outcode(tree *t, int eflag)
{
	int p, q;
	tree *tt;
	if(t==0)
		return;
	if(t->type!=NOT && t->type!=';')
		runq->iflast = 0;
	switch(t->type){
	default:
		pfmt(err, "bad type %d in outcode\n", t->type);
		break;
	case '$':
		emitf(Xmark);
		outcode(c0, eflag);
		emitf(Xdol);
		break;
	case '"':
		emitf(Xmark);
		outcode(c0, eflag);
		emitf(Xqdol);
		break;
	case SUB:
		emitf(Xmark);
		outcode(c0, eflag);
		emitf(Xmark);
		outcode(c1, eflag);
		emitf(Xsub);
		break;
	case '&':
		emitf(Xasync);
		if(havefork){
			p = emiti(0);
			outcode(c0, eflag);
			emitf(Xexit);
			stuffdot(p);
		} else
			emits(fnstr(c0));
		break;
	case ';':
		outcode(c0, eflag);
		outcode(c1, eflag);
		break;
	case '^':
		emitf(Xmark);
		outcode(c1, eflag);
		emitf(Xmark);
		outcode(c0, eflag);
		emitf(Xconc);
		break;
	case '`':
		emitf(Xbackq);
		if(havefork){
			p = emiti(0);
			outcode(c0, 0);
			emitf(Xexit);
			stuffdot(p);
		} else
			emits(fnstr(c0));
		break;
	case ANDAND:
		outcode(c0, 0);
		emitf(Xtrue);
		p = emiti(0);
		outcode(c1, eflag);
		stuffdot(p);
		break;
	case ARGLIST:
		outcode(c1, eflag);
		outcode(c0, eflag);
		break;
	case BANG:
		outcode(c0, eflag);
		emitf(Xbang);
		break;
	case PCMD:
	case BRACE:
		outcode(c0, eflag);
		break;
	case COUNT:
		emitf(Xmark);
		outcode(c0, eflag);
		emitf(Xcount);
		break;
	case FN:
		emitf(Xmark);
		outcode(c0, eflag);
		if(c1){
			emitf(Xfn);
			p = emiti(0);
			emits(fnstr(c1));
			outcode(c1, eflag);
			emitf(Xunlocal);	/* get rid of $* */
			emitf(Xreturn);
			stuffdot(p);
		}
		else
			emitf(Xdelfn);
		break;
	case IF:
		outcode(c0, 0);
		emitf(Xif);
		p = emiti(0);
		outcode(c1, eflag);
		emitf(Xwastrue);
		stuffdot(p);
		break;
	case NOT:
		if(!runq->iflast)
			yyerror("`if not' does not follow `if(...)'");
		emitf(Xifnot);
		p = emiti(0);
		outcode(c0, eflag);
		stuffdot(p);
		break;
	case OROR:
		outcode(c0, 0);
		emitf(Xfalse);
		p = emiti(0);
		outcode(c1, eflag);
		stuffdot(p);
		break;
	case PAREN:
		outcode(c0, eflag);
		break;
	case SIMPLE:
		emitf(Xmark);
		outcode(c0, eflag);
		emitf(Xsimple);
		if(eflag)
			emitf(Xeflag);
		break;
	case SUBSHELL:
		emitf(Xsubshell);
		if(havefork){
			p = emiti(0);
			outcode(c0, eflag);
			emitf(Xexit);
			stuffdot(p);
		} else
			emits(fnstr(c0));
		if(eflag)
			emitf(Xeflag);
		break;
	case SWITCH:
		codeswitch(t, eflag);
		break;
	case TWIDDLE:
		emitf(Xmark);
		outcode(c1, eflag);
		emitf(Xmark);
		outcode(c0, eflag);
		emitf(Xmatch);
		if(eflag)
			emitf(Xeflag);
		break;
	case WHILE:
		q = codep;
		outcode(c0, 0);
		if(q==codep)
			emitf(Xsettrue);	/* empty condition == while(true) */
		emitf(Xtrue);
		p = emiti(0);
		outcode(c1, eflag);
		emitf(Xjump);
		emiti(q);
		stuffdot(p);
		break;
	case WORDS:
		outcode(c1, eflag);
		outcode(c0, eflag);
		break;
	case FOR:
		emitf(Xmark);
		if(c1){
			outcode(c1, eflag);
			emitf(Xglob);
		}
		else{
			emitf(Xmark);
			emitf(Xword);
			emits(strdup("*"));
			emitf(Xdol);
		}
		emitf(Xmark);		/* dummy value for Xlocal */
		emitf(Xmark);
		outcode(c0, eflag);
		emitf(Xlocal);
		p = emitf(Xfor);
		q = emiti(0);
		outcode(c2, eflag);
		emitf(Xjump);
		emiti(p);
		stuffdot(q);
		emitf(Xunlocal);
		break;
	case WORD:
		emitf(Xword);
		emits(strdup(t->str));
		break;
	case DUP:
		if(t->rtype==DUPFD){
			emitf(Xdup);
			emiti(t->fd0);
			emiti(t->fd1);
		}
		else{
			emitf(Xclose);
			emiti(t->fd0);
		}
		outcode(c1, eflag);
		emitf(Xpopredir);
		break;
	case PIPEFD:
		emitf(Xpipefd);
		emiti(t->rtype);
		if(havefork){
			p = emiti(0);
			outcode(c0, eflag);
			emitf(Xexit);
			stuffdot(p);
		} else {
			emits(fnstr(c0));
		}
		break;
	case REDIR:
		emitf(Xmark);
		outcode(c0, eflag);
		emitf(Xglob);
		switch(t->rtype){
		case APPEND:
			emitf(Xappend);
			break;
		case WRITE:
			emitf(Xwrite);
			break;
		case READ:
		case HERE:
			emitf(Xread);
			break;
		case RDWR:
			emitf(Xrdwr);
			break;
		}
		emiti(t->fd0);
		outcode(c1, eflag);
		emitf(Xpopredir);
		break;
	case '=':
		tt = t;
		for(;t && t->type=='=';t = c2);
		if(t){
			for(t = tt;t->type=='=';t = c2){
				emitf(Xmark);
				outcode(c1, eflag);
				emitf(Xmark);
				outcode(c0, eflag);
				emitf(Xlocal);
			}
			outcode(t, eflag);
			for(t = tt; t->type=='='; t = c2)
				emitf(Xunlocal);
		}
		else{
			for(t = tt;t;t = c2){
				emitf(Xmark);
				outcode(c1, eflag);
				emitf(Xmark);
				outcode(c0, eflag);
				emitf(Xassign);
			}
		}
		t = tt;	/* so tests below will work */
		break;
	case PIPE:
		emitf(Xpipe);
		emiti(t->fd0);
		emiti(t->fd1);
		if(havefork){
			p = emiti(0);
			q = emiti(0);
			outcode(c0, eflag);
			emitf(Xexit);
			stuffdot(p);
		} else {
			emits(fnstr(c0));
			q = emiti(0);
		}
		outcode(c1, eflag);
		emitf(Xreturn);
		stuffdot(q);
		emitf(Xpipewait);
		break;
	}
	if(t->type!=NOT && t->type!=';')
		runq->iflast = t->type==IF;
	else if(c0) runq->iflast = c0->type==IF;
}
Exemple #2
0
 data eval_routine(routineNode rout, symrec ** symTable, list * routineList){
   data res;
   //recupera la routine e controlla se esiste
   routine * r = getRoutine(rout.name, routineList);
   if(r==NULL){
      yyerror("accessing unexisting procedure or function..");
      exit(NO_SUCH_PROCEDURE);
   }
   //dalla routine prendi gli i parametri
   form * forms;
   forms = r->parameters;
   //dal nodo passato prendi gli argomenti
   actual * aes;
   aes = rout.args;
   //HERE HAPPENS typechecking
   //we do minimal typechecking on length - the rest is left as exercise
   int flen = formLength(forms);
   int alen = actLength(aes);
   if(flen!=alen){
     yyerror("args len is different from formal length");
   }

   //qui fai il bind tra parametri e argomenti, mettendoli nella symbol TABLE
   // da ripassare a tutta la funzione di eval, usando il nodo expr come funzione di partenza
   symrec * rSymrec;
   rSymrec = NULL;

   for(int i = 0; i< flen; i++){
     form * f = getFormAtIndex(i,forms);
     if(f == NULL){
       //TODO place here the number of forms already used
       yyerror("execeed form list");
       exit(FORM_LIST_EXCEEDED);
     }
     actual * a = getActualAtIndex(i,aes);
     if (a == NULL){
       //TODO place here the number of args already used
       yyerror("execeed args list");
       exit(ARGS_LIST_EXCEEDED);
     }
     //eseguo dichiarazione e assegnazione nella symbol table che userà la routine
     type * t = basicDec(f->bt); //TODO: considered only basic type
     treeNode * dec = varDec(f->name,false,t);
     eval_identifier_declaration(dec->value.dec,&rSymrec,routineList);
     //cerca la var appena inserita e fai l'assignement
     identifier id; id.name = malloc(strlen(f->name)+1);
     strcpy(id.name,f->name);


     if (f->byref){
       if (a->expr->type != identifier_type){
         yyerror("incompatible arg for pass by ref");
         exit(ARGS_LIST_EXCEEDED);
       }
      symrec * tmp = getSymbolFromIdentifier(id,&rSymrec);
      symrec * tmp2 = getSymbolFromIdentifier(a->expr->value.id, symTable);
      tmp->value = tmp2->value;
     } else {
       //eval expr in current env, then assign it
       symrec * tmp = getSymbolFromIdentifier(id,&rSymrec);
       data e = eval(a->expr, symTable,routineList);
       spec_assignment(tmp,e, &rSymrec, routineList);
     }

    //  printf("%s", );

   }
  //eventually with return res = eval...
  eval(r->statementList, &rSymrec,routineList);

  if(r->type == procedure){
    res.type = no_op;
  }else{
    //qui cerca nella routine, nel suo return value il valore, puliscilo e resituicilo
    res = *r->returnValue;
    r->returnValue = NULL;
  }
  return res;
}
Exemple #3
0
//
// fixed point input
// required syntax is [+-][0[x]]d*
//
void
mpatofix(Mpint *a, char *as)
{
	int c, f;
	char *s;

	s = as;
	f = 0;
	mpmovecfix(a, 0);

	c = *s++;
	switch(c) {
	case '-':
		f = 1;

	case '+':
		c = *s++;
		if(c != '0')
			break;

	case '0':
		goto oct;
	}

	while(c) {
		if(c >= '0' && c <= '9') {
			mpmulcfix(a, 10);
			mpaddcfix(a, c-'0');
			c = *s++;
			continue;
		}
		goto bad;
	}
	goto out;

oct:
	c = *s++;
	if(c == 'x' || c == 'X')
		goto hex;
	while(c) {
		if(c >= '0' && c <= '7') {
			mpmulcfix(a, 8);
			mpaddcfix(a, c-'0');
			c = *s++;
			continue;
		}
		goto bad;
	}
	goto out;

hex:
	c = *s++;
	while(c) {
		if(c >= '0' && c <= '9') {
			mpmulcfix(a, 16);
			mpaddcfix(a, c-'0');
			c = *s++;
			continue;
		}
		if(c >= 'a' && c <= 'f') {
			mpmulcfix(a, 16);
			mpaddcfix(a, c+10-'a');
			c = *s++;
			continue;
		}
		if(c >= 'A' && c <= 'F') {
			mpmulcfix(a, 16);
			mpaddcfix(a, c+10-'A');
			c = *s++;
			continue;
		}
		goto bad;
	}

out:
	if(f)
		mpnegfix(a);
	return;

bad:
	yyerror("set ovf in mpatov: %s", as);
	mpmovecfix(a, 0);
}
Exemple #4
0
void
typecheckrange(Node *n)
{
	char *why;
	Type *t, *t1, *t2;
	Node *v1, *v2;
	NodeList *ll;

	// delicate little dance.  see typecheckas2
	for(ll=n->list; ll; ll=ll->next)
		if(ll->n->defn != n)
			typecheck(&ll->n, Erv | Easgn);

	typecheck(&n->right, Erv);
	if((t = n->right->type) == T)
		goto out;
	if(isptr[t->etype] && isfixedarray(t->type))
		t = t->type;
	n->type = t;

	switch(t->etype) {
	default:
		yyerror("cannot range over %lN", n->right);
		goto out;

	case TARRAY:
		t1 = types[TINT];
		t2 = t->type;
		break;

	case TMAP:
		t1 = t->down;
		t2 = t->type;
		break;

	case TCHAN:
		if(!(t->chan & Crecv)) {
			yyerror("invalid operation: range %N (receive from send-only type %T)", n->right, n->right->type);
			goto out;
		}
		t1 = t->type;
		t2 = nil;
		if(count(n->list) == 2)
			goto toomany;
		break;

	case TSTRING:
		t1 = types[TINT];
		t2 = runetype;
		break;
	}

	if(count(n->list) > 2) {
	toomany:
		yyerror("too many variables in range");
	}

	v1 = n->list->n;
	v2 = N;
	if(n->list->next)
		v2 = n->list->next->n;

	if(v1->defn == n)
		v1->type = t1;
	else if(v1->type != T && assignop(t1, v1->type, &why) == 0)
		yyerror("cannot assign type %T to %lN in range%s", t1, v1, why);
	if(v2) {
		if(v2->defn == n)
			v2->type = t2;
		else if(v2->type != T && assignop(t2, v2->type, &why) == 0)
			yyerror("cannot assign type %T to %lN in range%s", t2, v2, why);
	}

out:
	typechecklist(n->nbody, Etop);

	// second half of dance
	n->typecheck = 1;
	for(ll=n->list; ll; ll=ll->next)
		if(ll->n->typecheck == 0)
			typecheck(&ll->n, Erv | Easgn);
}
Exemple #5
0
 //We assume here typechecking has already happened
 data operation(int oper, data e1, data e2){
   data res;
   basic b;
   //pointer to a funcion that takes two int input and return an int
   int (*funIntPtr)(int,int);
   float (*funFloatPtr)(float,float);
   bool (*funBoolFloatPrt)(float,float);
   bool (*funBoolIntPrt)(int,int);
   bool (*funBoolPtr)(bool,bool);

   funIntPtr = NULL;
   funFloatPtr= NULL;
   funBoolFloatPrt = NULL;
   funBoolIntPrt = NULL;

   //I look for the function to be called
     switch (oper) {
       case MINUS:
         //*functionPtr = &subInt;
         switch (e1.b.type) {
           case basic_int_value:funIntPtr = subInt;break;
           case basic_float_value:funFloatPtr = subFloat;break;
           case basic_boolean_value:
             yyerror("boolean arithmetic operation are NOT_ALLOWED");
             exit(NOT_ALLOWED);
             break;
           case undef:
           default:
             yyerror("operation unmanaged type...");
             exit(BUGGY_THE_CLOWN);
             break;
           }
         break;
       case PLUS :
         switch (e1.b.type) {
           case basic_int_value:funIntPtr = addInt;break;
           case basic_float_value:funFloatPtr = addFloat;break;
           case basic_boolean_value:
             yyerror("boolean arithmetic operation are NOT_ALLOWED");
             exit(NOT_ALLOWED);
             break;
           case undef:
           default:
             yyerror("operation unmanaged type...");
             exit(BUGGY_THE_CLOWN);
             break;
         }
         break;
       case MULTIPLY:
         switch (e1.b.type) {
           case basic_int_value:funIntPtr = mulInt;break;
           case basic_float_value:funFloatPtr = mulFloat;break;
           case basic_boolean_value:
             yyerror("boolean arithmetic operation are NOT_ALLOWED");
             exit(NOT_ALLOWED);
             break;
           case undef:
           default:
             yyerror("operation unmanaged type...");
             exit(BUGGY_THE_CLOWN);
             break;
         }
         break;
       case DIVIDE :
         switch (e1.b.type) {
           case basic_int_value:funIntPtr = divInt;break;
           case basic_float_value:funFloatPtr = divFloat;break;
           case basic_boolean_value:
             yyerror("boolean arithmetic operation are NOT_ALLOWED");
             exit(NOT_ALLOWED);
             break;
           case undef:
           default:
            yyerror("operation unmanaged type...");
            exit(BUGGY_THE_CLOWN);
            break;
         }
         break;
       case LT :
         { switch (e1.b.type) {
           case basic_int_value:funBoolIntPrt = ltInt;break;
           case basic_float_value:funBoolFloatPrt = ltFloat;break;
           case basic_boolean_value:
             yyerror("boolean arithmetic operation are NOT_ALLOWED");
             exit(NOT_ALLOWED);
             break;
           case undef:
           default:
             yyerror("operation unmanaged type...");
             exit(BUGGY_THE_CLOWN);
             break;
           }
         }
         break;
       case GT :
         {switch (e1.b.type) {
           case basic_int_value:funBoolIntPrt = gtInt;break;
           case basic_float_value:funBoolFloatPrt = gtFloat;break;
           case basic_boolean_value:
             yyerror("boolean arithmetic operation are NOT_ALLOWED");
             exit(NOT_ALLOWED);
             break;
           case undef:
           default:
             yyerror("operation unmanaged type...");
             exit(BUGGY_THE_CLOWN);
             break;
           }
         }
         break;
       case GE :
         {switch (e1.b.type) {
           case basic_int_value:funBoolIntPrt = geInt;break;
           case basic_float_value:funBoolFloatPrt = geFloat;break;
           case basic_boolean_value:
             yyerror("boolean arithmetic operation are NOT_ALLOWED");
             exit(NOT_ALLOWED);
             break;
           case undef:
           default:
             yyerror("operation unmanaged type...");
             exit(BUGGY_THE_CLOWN);
             break;
           }
         }
         break;
       case LE :
         {switch (e1.b.type) {
           case basic_int_value:funBoolIntPrt = leInt;break;
           case basic_float_value:funBoolFloatPrt = leFloat;break;
           case basic_boolean_value:
             yyerror("boolean arithmetic operation are NOT_ALLOWED");
             exit(NOT_ALLOWED);
             break;
           case undef:
           default:
             yyerror("operation unmanaged type...");
             exit(BUGGY_THE_CLOWN);
             break;
           }
         }
         break;
       case NE :
          {
           switch (e1.b.type) {
             case basic_int_value:funBoolIntPrt = neInt;break;
             case basic_float_value:funBoolFloatPrt = neFloat;break;
             case basic_boolean_value:
               yyerror("boolean arithmetic operation are NOT_ALLOWED");
               exit(NOT_ALLOWED);
               break;
             case undef:
             default:
               yyerror("operation unmanaged type...");
               exit(BUGGY_THE_CLOWN);
               break;
             }
           }
         break;
       case EQ :
        {
          switch (e1.b.type) {
           case basic_int_value:funBoolIntPrt = eqInt;break;
           case basic_float_value:funBoolFloatPrt = eqFloat;break;
           case basic_boolean_value: funBoolPtr = eqBool;break;
           case undef:
           default:
             yyerror("operation unmanaged type...");
             exit(BUGGY_THE_CLOWN);
             break;
           }
         }
         break;
       default:
         yyerror("what now?");
         exit(BUGGY_THE_CLOWN);
         break;
      }
    //look for values to be used
    if( funIntPtr == NULL && funFloatPtr == NULL &&
        funBoolIntPrt == NULL && funBoolFloatPrt == NULL &&
        funBoolPtr == NULL
        ){
      yyerror("no function found for the specified operation..");
      exit(BUGGY_THE_CLOWN);
    }
    res.type = basic_dataType;
    switch (e1.b.type) {
      case basic_int_value:
        {
          if(funIntPtr!=NULL){

            if(oper == EQUALS){
              //il risultato è booleano
              res.b.type = basic_boolean_value;
              res.b.b = funIntPtr(e1.b.i, e2.b.i);
            }else{
              res.b.type = e1.b.type;//inherithed
              res.b.i = funIntPtr(e1.b.i, e2.b.i);
            }
          }else if(funBoolIntPrt!=NULL){
            //evaluating something like int < int or int == int
            res.b.type = basic_boolean_value;
            res.b.b = funBoolIntPrt(e1.b.i, e2.b.i);
          }else{
            yyerror("reached unexpected state..");
            exit(BUGGY_THE_CLOWN);
          }

        }
        break;
      case basic_float_value:
        {
          if(funFloatPtr!=NULL){
            if(oper == EQUALS){
              //il risultato è booleano
              res.b.type = basic_boolean_value;
              res.b.b = funFloatPtr(e1.b.f, e2.b.f);
            }else{
              res.b.type = e1.b.type;//inherithed
              res.b.f = funFloatPtr(e1.b.f, e2.b.f);
            }
          }else if(funBoolFloatPrt!=NULL){
            res.b.type = basic_boolean_value;
            res.b.b = funBoolFloatPrt(e1.b.f, e2.b.f);
          }else{
            yyerror("reached unexpected state..");
            exit(BUGGY_THE_CLOWN);
          }
        }
        break;
      case basic_boolean_value:
        {
          if(funFloatPtr!=NULL || funBoolFloatPrt!=NULL ||
            funBoolIntPrt!=NULL ||  funIntPtr!=NULL){
              yyerror("reached unexpected state..");
              exit(BUGGY_THE_CLOWN);
          }else{
            res.b.type =  e1.b.type;//inherithed
            res.b.b = funBoolPtr(e1.b.b, e2.b.b);
          }
        }
        break;
      default:
        yyerror("no data found for the specified operation..");
        exit(BUGGY_THE_CLOWN);
    }
   return res;
 }
Exemple #6
0
int add_object_sections(NAME_LIST *section_name_list)
{
    OBJECT_FILE **current;
    Elf_Scn *elf_section;
    Elf32_Shdr *shdr;
    NAME_LIST *section_name;
    Elf_Scn **array;
    int scns_available;
    int scns_added;
    array_index_t link_index;
    int page_links;
    const char *input_name;

    scns_added = scns_available = 0;
    array = NULL;
    array_index_init( &link_index, &link_array );
    current = (OBJECT_FILE **)array_index_next_page(
        &link_index, &page_links );
    while (current)
    {
        elf_section = NULL;
        while ((elf_section = elf_nextscn((*current)->elf, elf_section)) != 0)
        {
            shdr = elf32_getshdr(elf_section);
            elfcheck( shdr != NULL );
            if ( shdr->sh_type == SHT_PROGBITS ||
                 shdr->sh_type == SHT_NOBITS )
            {
                input_name = (*current)->strings+shdr->sh_name;
                for ( section_name = section_name_list ; section_name ;
                      section_name = section_name->next )
                {
                    if (strcmp( input_name, section_name->name) == 0)
                    {
                        if ((shdr->sh_flags & SHF_REFERENCED) == 0)
                        {
                            if ( scns_added >= scns_available )
                            {
                                array_update( &scn_array, scns_added );
                                scns_added = 0;
                                array = array_alloc( &scn_array,
                                                     &scns_available );
                            }
                            *array++ = elf_section;
                            ++scns_added;
//                            elf_flagshdr( elf_section, ELF_C_SET, SHF_REFERENCED );
                            shdr->sh_flags |= SHF_REFERENCED;
                        }
                        else
                        {
                            yyerror( "Input section is referenced twice" );
                        }
                        break;
                    }
                }
            }
        }
        ++current;
        if ( --page_links == 0 )
        {
            current = (OBJECT_FILE **)array_index_next_page(
                &link_index, &page_links );
        }
    }
    array_update( &scn_array, scns_added );
    return 1;
}
Exemple #7
0
/*
** yyparse - return 0 if worked, 1 if syntax error not recovered from
*/
int
yyparse()
{
	register YYSTYPE *yypvt;	/* top of value stack for $vars */
	unsigned yymaxdepth = YYMAXDEPTH;

	/*
	** Initialize externals - yyparse may be called more than once
	*/
	yyv = (YYSTYPE*)malloc(yymaxdepth*sizeof(YYSTYPE));
	yys = (int*)malloc(yymaxdepth*sizeof(int));
	if (!yyv || !yys)
	{
		yyerror( "out of memory" );
		return(1);
	}
	yypv = &yyv[-1];
	yyps = &yys[-1];
	yystate = 0;
	yytmp = 0;
	yynerrs = 0;
	yyerrflag = 0;
	yychar = -1;

	goto yystack;
	{
		register YYSTYPE *yy_pv;	/* top of value stack */
		register int *yy_ps;		/* top of state stack */
		register int yy_state;		/* current state */
		register int  yy_n;		/* internal state number info */

		/*
		** get globals into registers.
		** branch to here only if YYBACKUP was called.
		*/
	yynewstate:
		yy_pv = yypv;
		yy_ps = yyps;
		yy_state = yystate;
		goto yy_newstate;

		/*
		** get globals into registers.
		** either we just started, or we just finished a reduction
		*/
	yystack:
		yy_pv = yypv;
		yy_ps = yyps;
		yy_state = yystate;

		/*
		** top of for (;;) loop while no reductions done
		*/
	yy_stack:
		/*
		** put a state and value onto the stacks
		*/
#if YYDEBUG
		/*
		** if debugging, look up token value in list of value vs.
		** name pairs.  0 and negative (-1) are special values.
		** Note: linear search is used since time is not a real
		** consideration while debugging.
		*/
		if ( yydebug )
		{
			register int yy_i;

			(void)printf( "State %d, token ", yy_state );
			if ( yychar == 0 )
				(void)printf( "end-of-file\n" );
			else if ( yychar < 0 )
				(void)printf( "-none-\n" );
			else
			{
				for ( yy_i = 0; yytoks[yy_i].t_val >= 0;
					yy_i++ )
				{
					if ( yytoks[yy_i].t_val == yychar )
						break;
				}
				(void)printf( "%s\n", yytoks[yy_i].t_name );
			}
		}
#endif /* YYDEBUG */
		if ( ++yy_ps >= &yys[ yymaxdepth ] )	/* room on stack? */
		{
			/*
			** reallocate and recover.  Note that pointers
			** have to be reset, or bad things will happen
			*/
			int yyps_index = (yy_ps - yys);
			int yypv_index = (yy_pv - yyv);
			int yypvt_index = (yypvt - yyv);
			yymaxdepth += YYMAXDEPTH;
			yyv = (YYSTYPE*)realloc((char*)yyv,
				yymaxdepth * sizeof(YYSTYPE));
			yys = (int*)realloc((char*)yys,
				yymaxdepth * sizeof(int));
			if (!yyv || !yys)
			{
				yyerror( "yacc stack overflow" );
				return(1);
			}
			yy_ps = yys + yyps_index;
			yy_pv = yyv + yypv_index;
			yypvt = yyv + yypvt_index;
		}
		*yy_ps = yy_state;
		*++yy_pv = yyval;

		/*
		** we have a new state - find out what to do
		*/
	yy_newstate:
		if ( ( yy_n = yypact[ yy_state ] ) <= YYFLAG )
			goto yydefault;		/* simple state */
#if YYDEBUG
		/*
		** if debugging, need to mark whether new token grabbed
		*/
		yytmp = yychar < 0;
#endif
		if ( ( yychar < 0 ) && ( ( yychar = yylex() ) < 0 ) )
			yychar = 0;		/* reached EOF */
#if YYDEBUG
		if ( yydebug && yytmp )
		{
			register int yy_i;

			(void)printf( "Received token " );
			if ( yychar == 0 )
				(void)printf( "end-of-file\n" );
			else if ( yychar < 0 )
				(void)printf( "-none-\n" );
			else
			{
				for ( yy_i = 0; yytoks[yy_i].t_val >= 0;
					yy_i++ )
				{
					if ( yytoks[yy_i].t_val == yychar )
						break;
				}
				(void)printf( "%s\n", yytoks[yy_i].t_name );
			}
		}
#endif /* YYDEBUG */
		if ( ( ( yy_n += yychar ) < 0 ) || ( yy_n >= YYLAST ) )
			goto yydefault;
		if ( yychk[ yy_n = yyact[ yy_n ] ] == yychar )	/*valid shift*/
		{
			yychar = -1;
			yyval = yylval;
			yy_state = yy_n;
			if ( yyerrflag > 0 )
				yyerrflag--;
			goto yy_stack;
		}

	yydefault:
		if ( ( yy_n = yydef[ yy_state ] ) == -2 )
		{
#if YYDEBUG
			yytmp = yychar < 0;
#endif
			if ( ( yychar < 0 ) && ( ( yychar = yylex() ) < 0 ) )
				yychar = 0;		/* reached EOF */
#if YYDEBUG
			if ( yydebug && yytmp )
			{
				register int yy_i;

				(void)printf( "Received token " );
				if ( yychar == 0 )
					(void)printf( "end-of-file\n" );
				else if ( yychar < 0 )
					(void)printf( "-none-\n" );
				else
				{
					for ( yy_i = 0;
						yytoks[yy_i].t_val >= 0;
						yy_i++ )
					{
						if ( yytoks[yy_i].t_val
							== yychar )
						{
							break;
						}
					}
					(void)printf( "%s\n", yytoks[yy_i].t_name );
				}
			}
#endif /* YYDEBUG */
			/*
			** look through exception table
			*/
			{
				register int *yyxi = yyexca;

				while ( ( *yyxi != -1 ) ||
					( yyxi[1] != yy_state ) )
				{
					yyxi += 2;
				}
				while ( ( *(yyxi += 2) >= 0 ) &&
					( *yyxi != yychar ) )
					;
				if ( ( yy_n = yyxi[1] ) < 0 )
					YYACCEPT;
			}
		}

		/*
		** check for syntax error
		*/
		if ( yy_n == 0 )	/* have an error */
		{
			/* no worry about speed here! */
			switch ( yyerrflag )
			{
			case 0:		/* new error */
				yyerror( "syntax error" );
				goto skip_init;
			yyerrlab:
				/*
				** get globals into registers.
				** we have a user generated syntax type error
				*/
				yy_pv = yypv;
				yy_ps = yyps;
				yy_state = yystate;
				yynerrs++;
			skip_init:
			case 1:
			case 2:		/* incompletely recovered error */
					/* try again... */
				yyerrflag = 3;
				/*
				** find state where "error" is a legal
				** shift action
				*/
				while ( yy_ps >= yys )
				{
					yy_n = yypact[ *yy_ps ] + YYERRCODE;
					if ( yy_n >= 0 && yy_n < YYLAST &&
						yychk[yyact[yy_n]] == YYERRCODE)					{
						/*
						** simulate shift of "error"
						*/
						yy_state = yyact[ yy_n ];
						goto yy_stack;
					}
					/*
					** current state has no shift on
					** "error", pop stack
					*/
#if YYDEBUG
#	define _POP_ "Error recovery pops state %d, uncovers state %d\n"
					if ( yydebug )
						(void)printf( _POP_, *yy_ps,
							yy_ps[-1] );
#	undef _POP_
#endif
					yy_ps--;
					yy_pv--;
				}
				/*
				** there is no state on stack with "error" as
				** a valid shift.  give up.
				*/
				YYABORT;
			case 3:		/* no shift yet; eat a token */
#if YYDEBUG
				/*
				** if debugging, look up token in list of
				** pairs.  0 and negative shouldn't occur,
				** but since timing doesn't matter when
				** debugging, it doesn't hurt to leave the
				** tests here.
				*/
				if ( yydebug )
				{
					register int yy_i;

					(void)printf( "Error recovery discards " );
					if ( yychar == 0 )
						(void)printf( "token end-of-file\n" );
					else if ( yychar < 0 )
						(void)printf( "token -none-\n" );
					else
					{
						for ( yy_i = 0;
							yytoks[yy_i].t_val >= 0;
							yy_i++ )
						{
							if ( yytoks[yy_i].t_val
								== yychar )
							{
								break;
							}
						}
						(void)printf( "token %s\n",
							yytoks[yy_i].t_name );
					}
				}
#endif /* YYDEBUG */
				if ( yychar == 0 )	/* reached EOF. quit */
					YYABORT;
				yychar = -1;
				goto yy_newstate;
			}
		}/* end if ( yy_n == 0 ) */
		/*
		** reduction by production yy_n
		** put stack tops, etc. so things right after switch
		*/
#if YYDEBUG
		/*
		** if debugging, print the string that is the user's
		** specification of the reduction which is just about
		** to be done.
		*/
		if ( yydebug )
			(void)printf( "Reduce by (%d) \"%s\"\n",
				yy_n, yyreds[ yy_n ] );
#endif
		yytmp = yy_n;			/* value to switch over */
		yypvt = yy_pv;			/* $vars top of value stack */
		/*
		** Look in goto table for next state
		** Sorry about using yy_state here as temporary
		** register variable, but why not, if it works...
		** If yyr2[ yy_n ] doesn't have the low order bit
		** set, then there is no action to be done for
		** this reduction.  So, no saving & unsaving of
		** registers done.  The only difference between the
		** code just after the if and the body of the if is
		** the goto yy_stack in the body.  This way the test
		** can be made before the choice of what to do is needed.
		*/
		{
			/* length of production doubled with extra bit */
			register int yy_len = yyr2[ yy_n ];

			if ( !( yy_len & 01 ) )
			{
				yy_len >>= 1;
				yyval = ( yy_pv -= yy_len )[1];	/* $$ = $1 */
				yy_state = yypgo[ yy_n = yyr1[ yy_n ] ] +
					*( yy_ps -= yy_len ) + 1;
				if ( yy_state >= YYLAST ||
					yychk[ yy_state =
					yyact[ yy_state ] ] != -yy_n )
				{
					yy_state = yyact[ yypgo[ yy_n ] ];
				}
				goto yy_stack;
			}
			yy_len >>= 1;
			yyval = ( yy_pv -= yy_len )[1];	/* $$ = $1 */
			yy_state = yypgo[ yy_n = yyr1[ yy_n ] ] +
				*( yy_ps -= yy_len ) + 1;
			if ( yy_state >= YYLAST ||
				yychk[ yy_state = yyact[ yy_state ] ] != -yy_n )
			{
				yy_state = yyact[ yypgo[ yy_n ] ];
			}
		}
					/* save until reenter driver code */
		yystate = yy_state;
		yyps = yy_ps;
		yypv = yy_pv;
	}
Exemple #8
0
static int IsCf3Scalar(char *str)
{
    char *sp;
    char left = 'x', right = 'x';
    int dollar = false;
    int bracks = 0, vars = 0;

    CfDebug("IsCf3Scalar(%s) - syntax verify\n", str);

    if (str == NULL)
    {
        return false;
    }

    for (sp = str; *sp != '\0'; sp++)   /* check for varitems */
    {
        switch (*sp)
        {
        case '$':
            if (*(sp + 1) == '{' || *(sp + 1) == '(')
            {
                dollar = true;
            }
            break;
        case '(':
        case '{':
            if (dollar)
            {
                left = *sp;
                bracks++;
            }
            break;
        case ')':
        case '}':
            if (dollar)
            {
                bracks--;
                right = *sp;
            }
            break;
        }

        /* Some chars cannot be in variable ids, e.g.
           $(/bin/cat file) is legal in bash */

        if (bracks > 0)
        {
            switch (*sp)
            {
            case '/':
                return false;
            }
        }

        if (left == '(' && right == ')' && dollar && (bracks == 0))
        {
            vars++;
            dollar = false;
        }

        if (left == '{' && right == '}' && dollar && (bracks == 0))
        {
            vars++;
            dollar = false;
        }
    }

    if (dollar && (bracks != 0))
    {
        char output[CF_BUFSIZE];

        snprintf(output, CF_BUFSIZE, "Broken scalar variable syntax or bracket mismatch in \"%s\"", str);
        yyerror(output);
        return false;
    }

    CfDebug("Found %d variables in (%s)\n", vars, str);
    return vars;
}
Exemple #9
0
const char *ExtractInnerCf3VarString(const char *str, char *substr)
{
    const char *sp;
    int bracks = 1;

    CfDebug("ExtractInnerVarString( %s ) - syntax verify\n", str);

    if (str == NULL || strlen(str) == 0)
    {
        return NULL;
    }

    memset(substr, 0, CF_BUFSIZE);

    if (*(str + 1) != '(' && *(str + 1) != '{')
    {
        return NULL;
    }

/* Start this from after the opening $( */

    for (sp = str + 2; *sp != '\0'; sp++)       /* check for varitems */
    {
        switch (*sp)
        {
        case '(':
        case '{':
            bracks++;
            break;
        case ')':
        case '}':
            bracks--;
            break;

        default:
            if (isalnum((int) *sp) || strchr("_[]$.:-", *sp))
            {
            }
            else
            {
                CfDebug("Illegal character found: '%c'\n", *sp);
                CfDebug("Illegal character somewhere in variable \"%s\" or nested expansion", str);
            }
        }

        if (bracks == 0)
        {
            strncpy(substr, str + 2, sp - str - 2);
            CfDebug("Returning substring value %s\n", substr);
            return substr;
        }
    }

    if (bracks != 0)
    {
        char output[CF_BUFSIZE];

        if (strlen(substr) > 0)
        {
            snprintf(output, CF_BUFSIZE, "Broken variable syntax or bracket mismatch - inner (%s/%s)", str, substr);
            yyerror(output);
        }
        return NULL;
    }

    return sp - 1;
}
Exemple #10
0
int yyparse( void )
{
    short yypnum;
    short yyi, yylhs;
    YYACTTYPE yyaction;
    YYTOKENTYPE yytoken;
    YYACTTYPE yys[MAXDEPTH], *yysp;
    YYSTYPE yyv[MAXDEPTH], *yyvp;
    short yyerrflag;

    yyerrflag = 0;
    yysp = yys;
    yyvp = yyv;
    *yysp = YYSTART;
    yytoken = yylex();
    for( ;; ) {
yynewact:
        yyaction = find_action( *yysp, yytoken );
        if( yyaction == YYNOACTION ) {
            yyaction = find_action( *yysp, YYDEFTOKEN );
            if( yyaction == YYNOACTION ) {
                switch( yyerrflag ) {
                case 0:
                    yyerror( "syntax error" );
                    YYERROR;
yyerrlab:
                case 1:
                case 2:
                    yyerrflag = 3;
                    while( yysp >= yys ) {
                        yyaction = find_action( *yysp, YYERRTOKEN );
                        if( yyaction != YYNOACTION && yyaction < YYUSED ) {
                            *++yysp = yyaction;
                            ++yyvp;
                            goto yynewact;
                        }
                        --yysp;
                        --yyvp;
                    }
                    YYABORT;
                case 3:
                    if( yytoken == YYEOFTOKEN )
                        YYABORT;
                    yytoken = yylex();
                    goto yynewact;
                }
            }
        }
        if( yyaction < YYUSED ) {
            if( yyaction == YYSTOP ) {
                YYACCEPT;
            }
            *++yysp = yyaction;
            *++yyvp = yylval;
            if( yyerrflag )
                --yyerrflag;
            yytoken = yylex();
        } else {
            yypnum = yyaction - YYUSED;
            yyi = yyplentab[yypnum];
            yysp -= yyi;
            yyvp -= yyi;
            yylhs = yyplhstab[yypnum];
            if( yysp < yys ) {
                printf( "stack underflow\n" );
                YYABORT;
            }
            yyaction = find_action( *yysp, yylhs );
            if( yyaction == YYNOACTION ) {
                printf( "missing nonterminal\n" );
                YYABORT;
            }
            *++yysp = yyaction;
            ++yyvp;
            switch( yypnum ) {

            default:
                yyval = yyvp[0];
            }
            *yyvp = yyval;
        }
    }
}
Exemple #11
0
void
pragvararg(void)
{
	Sym *s;
	int n, c;
	char *t;
	Rune r;
	Type *ty;

	if(!debug['F'])
		goto out;
	s = getsym();
	if(s && strcmp(s->name, "argpos") == 0)
		goto ckpos;
	if(s && strcmp(s->name, "type") == 0)
		goto cktype;
	if(s && strcmp(s->name, "flag") == 0)
		goto ckflag;
	yyerror("syntax in #pragma varargck");
	goto out;

ckpos:
/*#pragma	varargck	argpos	warn	2*/
	s = getsym();
	if(s == S)
		goto bad;
	n = getnsn();
	if(n < 0)
		goto bad;
	newname(s->name, n);
	goto out;

ckflag:
/*#pragma	varargck	flag	'c'*/
	c = getnsc();
	if(c != '\'')
		goto bad;
	c = getr();
	if(c == '\\')
		c = getr();
	else if(c == '\'')
		goto bad;
	if(c == '\n')
		goto bad;
	if(getc() != '\'')
		goto bad;
	argflag(c, Fignor);
	goto out;

cktype:
/*#pragma	varargck	type	O	int*/
	c = getnsc();
	if(c != '"')
		goto bad;
	t = fmtbuf;
	for(;;) {
		r = getr();
		if(r == ' ' || r == '\n')
			goto bad;
		if(r == '"')
			break;
		t += runetochar(t, &r);
	}
	*t = 0;
	t = strdup(fmtbuf);
	s = getsym();
	if(s == S)
		goto bad;
	ty = s->type;
	while((c = getnsc()) == '*')
		ty = typ(TIND, ty);
	unget(c);
	newprot(s, ty, t);
	goto out;

bad:
	yyerror("syntax in #pragma varargck");

out:
	while(getnsc() != '\n')
		;
}
Exemple #12
0
int
yyparse(void)
{
	struct
	{
		YYSTYPE	yyv;
		int	yys;
	} yys[YYMAXDEPTH], *yyp, *yypt;
	short *yyxi;
	int yyj, yym, yystate, yyn, yyg;
	long yychar;
	YYSTYPE save1, save2;
	int save3, save4;

	save1 = yylval;
	save2 = yyval;
	save3 = yynerrs;
	save4 = yyerrflag;

	yystate = 0;
	yychar = -1;
	yynerrs = 0;
	yyerrflag = 0;
	yyp = &yys[-1];
	goto yystack;

ret0:
	yyn = 0;
	goto ret;

ret1:
	yyn = 1;
	goto ret;

ret:
	yylval = save1;
	yyval = save2;
	yynerrs = save3;
	yyerrflag = save4;
	return yyn;

yystack:
	/* put a state and value onto the stack */
	if(yydebug >= 4)
		fprint(2, "char %s in %s", yytokname(yychar), yystatname(yystate));

	yyp++;
	if(yyp >= &yys[YYMAXDEPTH]) {
		yyerror("yacc stack overflow");
		goto ret1;
	}
	yyp->yys = yystate;
	yyp->yyv = yyval;

yynewstate:
	yyn = yypact[yystate];
	if(yyn <= YYFLAG)
		goto yydefault; /* simple state */
	if(yychar < 0)
		yychar = yylex1();
	yyn += yychar;
	if(yyn < 0 || yyn >= YYLAST)
		goto yydefault;
	yyn = yyact[yyn];
	if(yychk[yyn] == yychar) { /* valid shift */
		yychar = -1;
		yyval = yylval;
		yystate = yyn;
		if(yyerrflag > 0)
			yyerrflag--;
		goto yystack;
	}

yydefault:
	/* default state action */
	yyn = yydef[yystate];
	if(yyn == -2) {
		if(yychar < 0)
			yychar = yylex1();

		/* look through exception table */
		for(yyxi=yyexca;; yyxi+=2)
			if(yyxi[0] == -1 && yyxi[1] == yystate)
				break;
		for(yyxi += 2;; yyxi += 2) {
			yyn = yyxi[0];
			if(yyn < 0 || yyn == yychar)
				break;
		}
		yyn = yyxi[1];
		if(yyn < 0)
			goto ret0;
	}
	if(yyn == 0) {
		/* error ... attempt to resume parsing */
		switch(yyerrflag) {
		case 0:   /* brand new error */
			yyerror("syntax error");
			yynerrs++;
			if(yydebug >= 1) {
				fprint(2, "%s", yystatname(yystate));
				fprint(2, "saw %s\n", yytokname(yychar));
			}

		case 1:
		case 2: /* incompletely recovered error ... try again */
			yyerrflag = 3;

			/* find a state where "error" is a legal shift action */
			while(yyp >= yys) {
				yyn = yypact[yyp->yys] + YYERRCODE;
				if(yyn >= 0 && yyn < YYLAST) {
					yystate = yyact[yyn];  /* simulate a shift of "error" */
					if(yychk[yystate] == YYERRCODE)
						goto yystack;
				}

				/* the current yyp has no shift onn "error", pop stack */
				if(yydebug >= 2)
					fprint(2, "error recovery pops state %d, uncovers %d\n",
						yyp->yys, (yyp-1)->yys );
				yyp--;
			}
			/* there is no state on the stack with an error shift ... abort */
			goto ret1;

		case 3:  /* no shift yet; clobber input char */
			if(yydebug >= 2)
				fprint(2, "error recovery discards %s\n", yytokname(yychar));
			if(yychar == YYEOFCODE)
				goto ret1;
			yychar = -1;
			goto yynewstate;   /* try again in the same state */
		}
	}

	/* reduction by production yyn */
	if(yydebug >= 2)
		fprint(2, "reduce %d in:\n\t%s", yyn, yystatname(yystate));

	yypt = yyp;
	yyp -= yyr2[yyn];
	yyval = (yyp+1)->yyv;
	yym = yyn;

	/* consult goto table to find next state */
	yyn = yyr1[yyn];
	yyg = yypgo[yyn];
	yyj = yyg + yyp->yys + 1;

	if(yyj >= YYLAST || yychk[yystate=yyact[yyj]] != -yyn)
		yystate = yyact[yyg];
	switch(yym) {
		
case 1:
#line	41	"asm.y"
{
		assem(yypt[-0].yyv.inst);
	} break;
case 2:
#line	47	"asm.y"
{ yyval.inst = nil; } break;
case 3:
#line	49	"asm.y"
{
		if(yypt[-0].yyv.inst != nil) {
			yypt[-0].yyv.inst->link = yypt[-1].yyv.inst;
			yyval.inst = yypt[-0].yyv.inst;
		}
		else
			yyval.inst = yypt[-1].yyv.inst;
	} break;
case 4:
#line	60	"asm.y"
{
		yypt[-0].yyv.inst->sym = yypt[-2].yyv.sym;
		yyval.inst = yypt[-0].yyv.inst;
	} break;
case 5:
#line	65	"asm.y"
{
		heap(yypt[-3].yyv.ival, yypt[-1].yyv.ival, yypt[-0].yyv.string);
		yyval.inst = nil;
	} break;
case 6:
#line	70	"asm.y"
{
		yyval.inst = nil;
	} break;
case 8:
#line	77	"asm.y"
{
		yyval.ival = yypt[-0].yyv.ival;
	} break;
case 9:
#line	81	"asm.y"
{
		yypt[-0].yyv.sym->value = heapid++;
		yyval.ival = yypt[-0].yyv.sym->value;
	} break;
case 10:
#line	88	"asm.y"
{ yyval.string = nil; } break;
case 11:
#line	90	"asm.y"
{
		yyval.string = yypt[-0].yyv.string;
	} break;
case 12:
#line	96	"asm.y"
{
		yyval.list = newi(yypt[-0].yyv.ival, nil);
	} break;
case 13:
#line	100	"asm.y"
{
		yyval.list = newi(yypt[-0].yyv.ival, yypt[-2].yyv.list);
	} break;
case 14:
#line	106	"asm.y"
{
		yyval.inst = ai(yypt[-3].yyv.ival);
		yyval.inst->src = yypt[-2].yyv.addr;
		yyval.inst->dst = yypt[-0].yyv.addr;
	} break;
case 15:
#line	112	"asm.y"
{
		yyval.inst = ai(yypt[-5].yyv.ival);
		yyval.inst->src = yypt[-4].yyv.addr;
		yyval.inst->reg = yypt[-2].yyv.addr;
		yyval.inst->dst = yypt[-0].yyv.addr;
	} break;
case 16:
#line	119	"asm.y"
{
		yyval.inst = ai(yypt[-3].yyv.ival);
		yyval.inst->src = yypt[-2].yyv.addr;
		yyval.inst->dst = yypt[-0].yyv.addr;
	} break;
case 17:
#line	125	"asm.y"
{
		yyval.inst = ai(yypt[-1].yyv.ival);
		yyval.inst->dst = yypt[-0].yyv.addr;
	} break;
case 18:
#line	130	"asm.y"
{
		yyval.inst = ai(yypt[-0].yyv.ival);
	} break;
case 19:
#line	136	"asm.y"
{
		data(DEFB, yypt[-2].yyv.ival, yypt[-0].yyv.list);
	} break;
case 20:
#line	140	"asm.y"
{
		data(DEFW, yypt[-2].yyv.ival, yypt[-0].yyv.list);
	} break;
case 21:
#line	144	"asm.y"
{
		data(DEFL, yypt[-2].yyv.ival, yypt[-0].yyv.list);
	} break;
case 22:
#line	148	"asm.y"
{
		data(DEFF, yypt[-2].yyv.ival, newi(dtocanon((double)yypt[-0].yyv.ival), nil));
	} break;
case 23:
#line	152	"asm.y"
{
		data(DEFF, yypt[-2].yyv.ival, newi(dtocanon(yypt[-0].yyv.fval), nil));
	} break;
case 24:
#line	156	"asm.y"
{
		if(strcmp(yypt[-0].yyv.sym->name, "Inf") == 0 || strcmp(yypt[-0].yyv.sym->name, "Infinity") == 0) {
			u.l = (uvlong)0x7ff00000<<32;
			data(DEFF, yypt[-2].yyv.ival, newi(dtocanon(u.d), nil));
		} else if(strcmp(yypt[-0].yyv.sym->name, "NaN") == 0) {
			u.l = ((uvlong)0x7fffffff<<32) | (uvlong)0xffffffffUL;
			data(DEFF, yypt[-2].yyv.ival, newi(dtocanon(u.d), nil));
		} else
			diag("bad value for real: %s", yypt[-0].yyv.sym->name);
	} break;
case 25:
#line	167	"asm.y"
{
		data(DEFF, yypt[-3].yyv.ival, newi(dtocanon(-(double)yypt[-0].yyv.ival), nil));
	} break;
case 26:
#line	171	"asm.y"
{
		data(DEFF, yypt[-3].yyv.ival, newi(dtocanon(-yypt[-0].yyv.fval), nil));
	} break;
case 27:
#line	175	"asm.y"
{
		if(strcmp(yypt[-0].yyv.sym->name, "Inf") == 0 || strcmp(yypt[-0].yyv.sym->name, "Infinity") == 0) {
			u.l = (uvlong)0xfff00000<<32;
			data(DEFF, yypt[-3].yyv.ival, newi(dtocanon(u.d), nil));
		} else
			diag("bad value for real: %s", yypt[-0].yyv.sym->name);
	} break;
case 28:
#line	183	"asm.y"
{
		data(DEFS, yypt[-2].yyv.ival, news(yypt[-0].yyv.string, nil));
	} break;
case 29:
#line	187	"asm.y"
{
		if(yypt[-2].yyv.sym->ds != 0)
			diag("%s declared twice", yypt[-2].yyv.sym->name);
		yypt[-2].yyv.sym->ds = yypt[-0].yyv.ival;
		yypt[-2].yyv.sym->value = dseg;
		dseg += yypt[-0].yyv.ival;
	} break;
case 30:
#line	195	"asm.y"
{
		ext(yypt[-4].yyv.ival, yypt[-2].yyv.ival, yypt[-0].yyv.string);
	} break;
case 31:
#line	199	"asm.y"
{
		mklink(yypt[-6].yyv.ival, yypt[-4].yyv.ival, yypt[-2].yyv.ival, yypt[-0].yyv.string);
	} break;
case 32:
#line	203	"asm.y"
{
		if(module != nil)
			diag("this module already defined as %s", yypt[-0].yyv.sym->name);
		else
			module = yypt[-0].yyv.sym;
	} break;
case 33:
#line	210	"asm.y"
{
		if(pcentry >= 0)
			diag("this module already has entry point %d, %d" , pcentry, dentry);
		pcentry = yypt[-2].yyv.ival;
		dentry = yypt[-0].yyv.ival;
	} break;
case 34:
#line	217	"asm.y"
{
		data(DEFA, yypt[-4].yyv.ival, newa(yypt[-2].yyv.ival, yypt[-0].yyv.ival));
	} break;
case 35:
#line	221	"asm.y"
{
		data(DIND, yypt[-2].yyv.ival, newa(yypt[-0].yyv.ival, 0));
	} break;
case 36:
#line	225	"asm.y"
{
		data(DAPOP, 0, newa(0, 0));
	} break;
case 37:
#line	229	"asm.y"
{
		ldts(yypt[-0].yyv.ival);
	} break;
case 38:
#line	233	"asm.y"
{
		excs(yypt[-0].yyv.ival);
	} break;
case 39:
#line	237	"asm.y"
{
		exc(yypt[-10].yyv.ival, yypt[-8].yyv.ival, yypt[-6].yyv.ival, yypt[-4].yyv.ival, yypt[-2].yyv.ival, yypt[-0].yyv.ival);
	} break;
case 40:
#line	241	"asm.y"
{
		etab(yypt[-2].yyv.string, yypt[-0].yyv.ival);
	} break;
case 41:
#line	245	"asm.y"
{
		etab(nil, yypt[-0].yyv.ival);
	} break;
case 42:
#line	249	"asm.y"
{
		source(yypt[-0].yyv.string);
	} break;
case 43:
#line	255	"asm.y"
{
		yyval.addr = aa(yypt[-0].yyv.ival);
		yyval.addr->mode = AXIMM;
		if(yyval.addr->val > 0x7FFF || yyval.addr->val < -0x8000)
			diag("immediate %d too large for middle operand", yyval.addr->val);
	} break;
case 44:
#line	262	"asm.y"
{
		if(yypt[-0].yyv.addr->mode == AMP)
			yypt[-0].yyv.addr->mode = AXINM;
		else
			yypt[-0].yyv.addr->mode = AXINF;
		if(yypt[-0].yyv.addr->mode == AXINM && (ulong)yypt[-0].yyv.addr->val > 0xFFFF)
			diag("register offset %d(mp) too large", yypt[-0].yyv.addr->val);
		if(yypt[-0].yyv.addr->mode == AXINF && (ulong)yypt[-0].yyv.addr->val > 0xFFFF)
			diag("register offset %d(fp) too large", yypt[-0].yyv.addr->val);
		yyval.addr = yypt[-0].yyv.addr;
	} break;
case 45:
#line	276	"asm.y"
{
		yyval.addr = aa(yypt[-0].yyv.ival);
		yyval.addr->mode = AIMM;
	} break;
case 46:
#line	281	"asm.y"
{
		yyval.addr = aa(0);
		yyval.addr->sym = yypt[-0].yyv.sym;
	} break;
case 48:
#line	289	"asm.y"
{
		yypt[-0].yyv.addr->mode |= AIND;
		yyval.addr = yypt[-0].yyv.addr;
	} break;
case 49:
#line	294	"asm.y"
{
		yypt[-1].yyv.addr->mode |= AIND;
		if(yypt[-1].yyv.addr->val & 3)
			diag("indirect offset must be word size");
		if(yypt[-1].yyv.addr->mode == (AMP|AIND) && ((ulong)yypt[-1].yyv.addr->val > 0xFFFF || (ulong)yypt[-3].yyv.ival > 0xFFFF))
			diag("indirect offset %d(%d(mp)) too large", yypt[-3].yyv.ival, yypt[-1].yyv.addr->val);
		if(yypt[-1].yyv.addr->mode == (AFP|AIND) && ((ulong)yypt[-1].yyv.addr->val > 0xFFFF || (ulong)yypt[-3].yyv.ival > 0xFFFF))
			diag("indirect offset %d(%d(fp)) too large", yypt[-3].yyv.ival, yypt[-1].yyv.addr->val);
		yypt[-1].yyv.addr->off = yypt[-1].yyv.addr->val;
		yypt[-1].yyv.addr->val = yypt[-3].yyv.ival;
		yyval.addr = yypt[-1].yyv.addr;
	} break;
case 51:
#line	310	"asm.y"
{
		yyval.addr = aa(yypt[-3].yyv.ival);
		yyval.addr->mode = AMP;
	} break;
case 52:
#line	315	"asm.y"
{
		yyval.addr = aa(yypt[-3].yyv.ival);
		yyval.addr->mode = AFP;
	} break;
case 54:
#line	323	"asm.y"
{
		yyval.ival = yypt[-0].yyv.sym->value;
	} break;
case 55:
#line	327	"asm.y"
{
		yyval.ival = -yypt[-0].yyv.ival;
	} break;
case 56:
#line	331	"asm.y"
{
		yyval.ival = yypt[-0].yyv.ival;
	} break;
case 57:
#line	335	"asm.y"
{
		yyval.ival = ~yypt[-0].yyv.ival;
	} break;
case 58:
#line	339	"asm.y"
{
		yyval.ival = yypt[-1].yyv.ival;
	} break;
case 60:
#line	346	"asm.y"
{
		yyval.ival = yypt[-2].yyv.ival + yypt[-0].yyv.ival;
	} break;
case 61:
#line	350	"asm.y"
{
		yyval.ival = yypt[-2].yyv.ival - yypt[-0].yyv.ival;
	} break;
case 62:
#line	354	"asm.y"
{
		yyval.ival = yypt[-2].yyv.ival * yypt[-0].yyv.ival;
	} break;
case 63:
#line	358	"asm.y"
{
		yyval.ival = yypt[-2].yyv.ival / yypt[-0].yyv.ival;
	} break;
case 64:
#line	362	"asm.y"
{
		yyval.ival = yypt[-2].yyv.ival % yypt[-0].yyv.ival;
	} break;
case 65:
#line	366	"asm.y"
{
		yyval.ival = yypt[-3].yyv.ival << yypt[-0].yyv.ival;
	} break;
case 66:
#line	370	"asm.y"
{
		yyval.ival = yypt[-3].yyv.ival >> yypt[-0].yyv.ival;
	} break;
case 67:
#line	374	"asm.y"
{
		yyval.ival = yypt[-2].yyv.ival & yypt[-0].yyv.ival;
	} break;
case 68:
#line	378	"asm.y"
{
		yyval.ival = yypt[-2].yyv.ival ^ yypt[-0].yyv.ival;
	} break;
case 69:
#line	382	"asm.y"
{
		yyval.ival = yypt[-2].yyv.ival | yypt[-0].yyv.ival;
	} break;
	}
	goto yystack;  /* stack new state and value */
}
Exemple #13
0
void
regopt(Prog *firstp)
{
	Reg *r, *r1;
	Prog *p;
	int i, z, nr;
	uint32 vreg;
	Bits bit;
	
	if(first == 0) {
		fmtinstall('Q', Qconv);
	}
	
	fixjmp(firstp);

	first++;
	if(debug['K']) {
		if(first != 13)
			return;
//		debug['R'] = 2;
//		debug['P'] = 2;
		print("optimizing %S\n", curfn->nname->sym);
	}

	// count instructions
	nr = 0;
	for(p=firstp; p!=P; p=p->link)
		nr++;

	// if too big dont bother
	if(nr >= 10000) {
//		print("********** %S is too big (%d)\n", curfn->nname->sym, nr);
		return;
	}

	firstr = R;
	lastr = R;

	/*
	 * control flow is more complicated in generated go code
	 * than in generated c code.  define pseudo-variables for
	 * registers, so we have complete register usage information.
	 */
	nvar = NREGVAR;
	memset(var, 0, NREGVAR*sizeof var[0]);
	for(i=0; i<NREGVAR; i++) {
		if(regnodes[i] == N)
			regnodes[i] = newname(lookup(regname[i]));
		var[i].node = regnodes[i];
	}

	regbits = RtoB(REGSP)|RtoB(REGLINK)|RtoB(REGPC);
	for(z=0; z<BITS; z++) {
		externs.b[z] = 0;
		params.b[z] = 0;
		consts.b[z] = 0;
		addrs.b[z] = 0;
		ovar.b[z] = 0;
	}

	// build list of return variables
	setoutvar();

	/*
	 * pass 1
	 * build aux data structure
	 * allocate pcs
	 * find use and set of variables
	 */
	nr = 0;
	for(p=firstp; p != P; p = p->link) {
		switch(p->as) {
		case ADATA:
		case AGLOBL:
		case ANAME:
		case ASIGNAME:
			continue;
		}
		r = rega();
		nr++;
		if(firstr == R) {
			firstr = r;
			lastr = r;
		} else {
			lastr->link = r;
			r->p1 = lastr;
			lastr->s1 = r;
			lastr = r;
		}
		r->prog = p;
		p->regp = r;

		r1 = r->p1;
		if(r1 != R) {
			switch(r1->prog->as) {
			case ARET:
			case AB:
			case ARFE:
				r->p1 = R;
				r1->s1 = R;
			}
		}

		// Avoid making variables for direct-called functions.
		if(p->as == ABL && p->to.type == D_EXTERN)
			continue;

		/*
		 * left side always read
		 */
		bit = mkvar(r, &p->from);
		for(z=0; z<BITS; z++)
			r->use1.b[z] |= bit.b[z];
		
		/*
		 * middle always read when present
		 */
		if(p->reg != NREG) {
			if(p->from.type != D_FREG)
				r->use1.b[0] |= RtoB(p->reg);
			else
				r->use1.b[0] |= FtoB(p->reg);
		}

		/*
		 * right side depends on opcode
		 */
		bit = mkvar(r, &p->to);
		if(bany(&bit))
		switch(p->as) {
		default:
			yyerror("reg: unknown op: %A", p->as);
			break;
		
		/*
		 * right side read
		 */
		case ATST:
		case ATEQ:
		case ACMP:
		case ACMN:
		case ACMPD:
		case ACMPF:
		rightread:
			for(z=0; z<BITS; z++)
				r->use2.b[z] |= bit.b[z];
			break;
			
		/*
		 * right side read or read+write, depending on middle
		 *	ADD x, z => z += x
		 *	ADD x, y, z  => z = x + y
		 */
		case AADD:
		case AAND:
		case AEOR:
		case ASUB:
		case ARSB:
		case AADC:
		case ASBC:
		case ARSC:
		case AORR:
		case ABIC:
		case ASLL:
		case ASRL:
		case ASRA:
		case AMUL:
		case AMULU:
		case ADIV:
		case AMOD:
		case AMODU:
		case ADIVU:
			if(p->reg != NREG)
				goto rightread;
			// fall through

		/*
		 * right side read+write
		 */
		case AADDF:
		case AADDD:
		case ASUBF:
		case ASUBD:
		case AMULF:
		case AMULD:
		case ADIVF:
		case ADIVD:
		case AMULA:
		case AMULAL:
		case AMULALU:
			for(z=0; z<BITS; z++) {
				r->use2.b[z] |= bit.b[z];
				r->set.b[z] |= bit.b[z];
			}
			break;

		/*
		 * right side write
		 */
		case ANOP:
		case AMOVB:
		case AMOVBU:
		case AMOVD:
		case AMOVDF:
		case AMOVDW:
		case AMOVF:
		case AMOVFW:
		case AMOVH:
		case AMOVHU:
		case AMOVW:
		case AMOVWD:
		case AMOVWF:
		case AMVN:
		case AMULL:
		case AMULLU:
			if((p->scond & C_SCOND) != C_SCOND_NONE)
				for(z=0; z<BITS; z++)
					r->use2.b[z] |= bit.b[z];
			for(z=0; z<BITS; z++)
				r->set.b[z] |= bit.b[z];
			break;

		/*
		 * funny
		 */
		case ABL:
			setaddrs(bit);
			break;
		}

		if(p->as == AMOVM) {
			z = p->to.offset;
			if(p->from.type == D_CONST)
				z = p->from.offset;
			for(i=0; z; i++) {
				if(z&1)
					regbits |= RtoB(i);
				z >>= 1;
			}
		}
	}
Exemple #14
0
void
genfuncname(struct table *tp, char *cname, char *fname, int type)
{
	char tmp[512], *xp;
	struct column *cp = NULL;

	if (tp == NULL)
		return;
	if (cname != NULL && (cp = findcolumn(tp, cname)) == NULL) {
		yyerror("cannot find column within table");
		return;
	}
	switch (type) {
	case DBOW_INSERT:
		if (tp->ifname != NULL) {
			yyerror("multiple insert definitions for table");
			return;
		}
		xp = "insert";
		break;
	case DBOW_DELETE:
		if (cp == NULL)
			return;
		if (cp->dfname != NULL) {
			yyerror("multiple insert definitions for column");
			return;
		}
		xp = "delete";
		break;
	case DBOW_SEARCH:
		if (cp == NULL)
			return;
		if (cp->sfname != NULL) {
			yyerror("multiple insert definitions for column");
			return;
		}
		xp = "find";
		break;
	case DBOW_UPDATE:
		if (cp == NULL)
			return;
		if (cp->ufname != NULL) {
			yyerror("multiple insert definitions for column");
			return;
		}
		xp = "update";
		break;
	}
	if (fname == NULL) {
		if (type != DBOW_INSERT)
			sprintf(tmp, "db_%s%sby%s", xp, tp->name, cp->name);
		else
			sprintf(tmp, "db_%s%s", xp, tp->name);
		xp = tmp;
	} else
		xp = fname;
	switch (type) {
	case DBOW_INSERT:
		tp->ifname = strdup(xp);
		break;
	case DBOW_DELETE:
		cp->dfname = strdup(xp);
		break;
	case DBOW_SEARCH:
		cp->sfname = strdup(xp);
		break;
	case DBOW_UPDATE:
		cp->ufname = strdup(xp);
		break;
	}
}
Exemple #15
0
int
yyparse(void)
{
	struct
	{
		YYSTYPE	yyv;
		int	yys;
	} yys[YYMAXDEPTH], *yyp, *yypt;
	short *yyxi;
	int yyj, yym, yystate, yyn, yyg;
	long yychar;
	YYSTYPE save1, save2;
	int save3, save4;

	save1 = yylval;
	save2 = yyval;
	save3 = yynerrs;
	save4 = yyerrflag;

	yystate = 0;
	yychar = -1;
	yynerrs = 0;
	yyerrflag = 0;
	yyp = &yys[-1];
	goto yystack;

ret0:
	yyn = 0;
	goto ret;

ret1:
	yyn = 1;
	goto ret;

ret:
	yylval = save1;
	yyval = save2;
	yynerrs = save3;
	yyerrflag = save4;
	return yyn;

yystack:
	/* put a state and value onto the stack */
	if(yydebug >= 4)
		fprint(2, "char %s in %s", yytokname(yychar), yystatname(yystate));

	yyp++;
	if(yyp >= &yys[YYMAXDEPTH]) {
		yyerror("yacc stack overflow");
		goto ret1;
	}
	yyp->yys = yystate;
	yyp->yyv = yyval;

yynewstate:
	yyn = yypact[yystate];
	if(yyn <= YYFLAG)
		goto yydefault; /* simple state */
	if(yychar < 0)
		yychar = yylex1();
	yyn += yychar;
	if(yyn < 0 || yyn >= YYLAST)
		goto yydefault;
	yyn = yyact[yyn];
	if(yychk[yyn] == yychar) { /* valid shift */
		yychar = -1;
		yyval = yylval;
		yystate = yyn;
		if(yyerrflag > 0)
			yyerrflag--;
		goto yystack;
	}

yydefault:
	/* default state action */
	yyn = yydef[yystate];
	if(yyn == -2) {
		if(yychar < 0)
			yychar = yylex1();

		/* look through exception table */
		for(yyxi=yyexca;; yyxi+=2)
			if(yyxi[0] == -1 && yyxi[1] == yystate)
				break;
		for(yyxi += 2;; yyxi += 2) {
			yyn = yyxi[0];
			if(yyn < 0 || yyn == yychar)
				break;
		}
		yyn = yyxi[1];
		if(yyn < 0)
			goto ret0;
	}
	if(yyn == 0) {
		/* error ... attempt to resume parsing */
		switch(yyerrflag) {
		case 0:   /* brand new error */
			yyerror("syntax error");
			yynerrs++;
			if(yydebug >= 1) {
				fprint(2, "%s", yystatname(yystate));
				fprint(2, "saw %s\n", yytokname(yychar));
			}

		case 1:
		case 2: /* incompletely recovered error ... try again */
			yyerrflag = 3;

			/* find a state where "error" is a legal shift action */
			while(yyp >= yys) {
				yyn = yypact[yyp->yys] + YYERRCODE;
				if(yyn >= 0 && yyn < YYLAST) {
					yystate = yyact[yyn];  /* simulate a shift of "error" */
					if(yychk[yystate] == YYERRCODE)
						goto yystack;
				}

				/* the current yyp has no shift onn "error", pop stack */
				if(yydebug >= 2)
					fprint(2, "error recovery pops state %d, uncovers %d\n",
						yyp->yys, (yyp-1)->yys );
				yyp--;
			}
			/* there is no state on the stack with an error shift ... abort */
			goto ret1;

		case 3:  /* no shift yet; clobber input char */
			if(yydebug >= 2)
				fprint(2, "error recovery discards %s\n", yytokname(yychar));
			if(yychar == YYEOFCODE)
				goto ret1;
			yychar = -1;
			goto yynewstate;   /* try again in the same state */
		}
	}

	/* reduction by production yyn */
	if(yydebug >= 2)
		fprint(2, "reduce %d in:\n\t%s", yyn, yystatname(yystate));

	yypt = yyp;
	yyp -= yyr2[yyn];
	yyval = (yyp+1)->yyv;
	yym = yyn;

	/* consult goto table to find next state */
	yyn = yyr1[yyn];
	yyg = yypgo[yyn];
	yyj = yyg + yyp->yys + 1;

	if(yyj >= YYLAST || yychk[yystate=yyact[yyj]] != -yyn)
		yystate = yyact[yyg];
	switch(yym) {
		
case 3:
#line	77	"cc.y"
{
		dodecl(xdecl, lastclass, lasttype, Z);
	} break;
case 5:
#line	82	"cc.y"
{
		lastdcl = T;
		firstarg = S;
		dodecl(xdecl, lastclass, lasttype, yypt[-0].yyv.node);
		if(lastdcl == T || lastdcl->etype != TFUNC) {
			diag(yypt[-0].yyv.node, "not a function");
			lastdcl = types[TFUNC];
		}
		thisfn = lastdcl;
		markdcl();
		firstdcl = dclstack;
		argmark(yypt[-0].yyv.node, 0);
	} break;
case 6:
#line	96	"cc.y"
{
		argmark(yypt[-2].yyv.node, 1);
	} break;
case 7:
#line	100	"cc.y"
{
		Node *n;

		n = revertdcl();
		if(n)
			yypt[-0].yyv.node = new(OLIST, n, yypt[-0].yyv.node);
		if(!debug['a'] && !debug['Z'])
			codgen(yypt[-0].yyv.node, yypt[-4].yyv.node);
	} break;
case 8:
#line	112	"cc.y"
{
		dodecl(xdecl, lastclass, lasttype, yypt[-0].yyv.node);
	} break;
case 9:
#line	116	"cc.y"
{
		yypt[-0].yyv.node = dodecl(xdecl, lastclass, lasttype, yypt[-0].yyv.node);
	} break;
case 10:
#line	120	"cc.y"
{
		doinit(yypt[-3].yyv.node->sym, yypt[-3].yyv.node->type, 0L, yypt[-0].yyv.node);
	} break;
case 13:
#line	128	"cc.y"
{
		yyval.node = new(OIND, yypt[-0].yyv.node, Z);
		yyval.node->garb = simpleg(yypt[-1].yyv.lval);
	} break;
case 15:
#line	136	"cc.y"
{
		yyval.node = yypt[-1].yyv.node;
	} break;
case 16:
#line	140	"cc.y"
{
		yyval.node = new(OFUNC, yypt[-3].yyv.node, yypt[-1].yyv.node);
	} break;
case 17:
#line	144	"cc.y"
{
		yyval.node = new(OARRAY, yypt[-3].yyv.node, yypt[-1].yyv.node);
	} break;
case 18:
#line	153	"cc.y"
{
		yyval.node = dodecl(adecl, lastclass, lasttype, Z);
	} break;
case 19:
#line	157	"cc.y"
{
		yyval.node = yypt[-1].yyv.node;
	} break;
case 20:
#line	163	"cc.y"
{
		dodecl(adecl, lastclass, lasttype, yypt[-0].yyv.node);
		yyval.node = Z;
	} break;
case 21:
#line	168	"cc.y"
{
		yypt[-0].yyv.node = dodecl(adecl, lastclass, lasttype, yypt[-0].yyv.node);
	} break;
case 22:
#line	172	"cc.y"
{
		long w;

		w = yypt[-3].yyv.node->sym->type->width;
		yyval.node = doinit(yypt[-3].yyv.node->sym, yypt[-3].yyv.node->type, 0L, yypt[-0].yyv.node);
		yyval.node = contig(yypt[-3].yyv.node->sym, yyval.node, w);
	} break;
case 23:
#line	180	"cc.y"
{
		yyval.node = yypt[-2].yyv.node;
		if(yypt[-0].yyv.node != Z) {
			yyval.node = yypt[-0].yyv.node;
			if(yypt[-2].yyv.node != Z)
				yyval.node = new(OLIST, yypt[-2].yyv.node, yypt[-0].yyv.node);
		}
	} break;
case 26:
#line	197	"cc.y"
{
		dodecl(pdecl, lastclass, lasttype, yypt[-0].yyv.node);
	} break;
case 28:
#line	207	"cc.y"
{
		lasttype = yypt[-0].yyv.type;
	} break;
case 30:
#line	212	"cc.y"
{
		lasttype = yypt[-0].yyv.type;
	} break;
case 32:
#line	218	"cc.y"
{
		lastfield = 0;
		edecl(CXXX, lasttype, S);
	} break;
case 34:
#line	226	"cc.y"
{
		dodecl(edecl, CXXX, lasttype, yypt[-0].yyv.node);
	} break;
case 36:
#line	233	"cc.y"
{
		lastbit = 0;
		firstbit = 1;
	} break;
case 37:
#line	238	"cc.y"
{
		yyval.node = new(OBIT, yypt[-2].yyv.node, yypt[-0].yyv.node);
	} break;
case 38:
#line	242	"cc.y"
{
		yyval.node = new(OBIT, Z, yypt[-0].yyv.node);
	} break;
case 39:
#line	250	"cc.y"
{
		yyval.node = (Z);
	} break;
case 41:
#line	257	"cc.y"
{
		yyval.node = new(OIND, (Z), Z);
		yyval.node->garb = simpleg(yypt[-0].yyv.lval);
	} break;
case 42:
#line	262	"cc.y"
{
		yyval.node = new(OIND, yypt[-0].yyv.node, Z);
		yyval.node->garb = simpleg(yypt[-1].yyv.lval);
	} break;
case 45:
#line	271	"cc.y"
{
		yyval.node = new(OFUNC, yypt[-3].yyv.node, yypt[-1].yyv.node);
	} break;
case 46:
#line	275	"cc.y"
{
		yyval.node = new(OARRAY, yypt[-3].yyv.node, yypt[-1].yyv.node);
	} break;
case 47:
#line	281	"cc.y"
{
		yyval.node = new(OFUNC, (Z), Z);
	} break;
case 48:
#line	285	"cc.y"
{
		yyval.node = new(OARRAY, (Z), yypt[-1].yyv.node);
	} break;
case 49:
#line	289	"cc.y"
{
		yyval.node = yypt[-1].yyv.node;
	} break;
case 51:
#line	296	"cc.y"
{
		yyval.node = new(OINIT, invert(yypt[-1].yyv.node), Z);
	} break;
case 52:
#line	302	"cc.y"
{
		yyval.node = new(OARRAY, yypt[-1].yyv.node, Z);
	} break;
case 53:
#line	306	"cc.y"
{
		yyval.node = new(OELEM, Z, Z);
		yyval.node->sym = yypt[-0].yyv.sym;
	} break;
case 56:
#line	315	"cc.y"
{
		yyval.node = new(OLIST, yypt[-2].yyv.node, yypt[-1].yyv.node);
	} break;
case 58:
#line	320	"cc.y"
{
		yyval.node = new(OLIST, yypt[-1].yyv.node, yypt[-0].yyv.node);
	} break;
case 61:
#line	328	"cc.y"
{
		yyval.node = new(OLIST, yypt[-1].yyv.node, yypt[-0].yyv.node);
	} break;
case 62:
#line	333	"cc.y"
{
		yyval.node = Z;
	} break;
case 63:
#line	337	"cc.y"
{
		yyval.node = invert(yypt[-0].yyv.node);
	} break;
case 65:
#line	345	"cc.y"
{
		yyval.node = new(OPROTO, yypt[-0].yyv.node, Z);
		yyval.node->type = yypt[-1].yyv.type;
	} break;
case 66:
#line	350	"cc.y"
{
		yyval.node = new(OPROTO, yypt[-0].yyv.node, Z);
		yyval.node->type = yypt[-1].yyv.type;
	} break;
case 67:
#line	355	"cc.y"
{
		yyval.node = new(ODOTDOT, Z, Z);
	} break;
case 68:
#line	359	"cc.y"
{
		yyval.node = new(OLIST, yypt[-2].yyv.node, yypt[-0].yyv.node);
	} break;
case 69:
#line	365	"cc.y"
{
		yyval.node = invert(yypt[-1].yyv.node);
	//	if(yypt[-1].yyv.node != Z)
	//		yyval.node = new(OLIST, yypt[-1].yyv.node, yyval.node);
		if(yyval.node == Z)
			yyval.node = new(OLIST, Z, Z);
	} break;
case 70:
#line	374	"cc.y"
{
		yyval.node = Z;
	} break;
case 71:
#line	378	"cc.y"
{
		yyval.node = new(OLIST, yypt[-1].yyv.node, yypt[-0].yyv.node);
	} break;
case 72:
#line	382	"cc.y"
{
		yyval.node = new(OLIST, yypt[-1].yyv.node, yypt[-0].yyv.node);
	} break;
case 74:
#line	389	"cc.y"
{
		yyval.node = new(OLIST, yypt[-1].yyv.node, yypt[-0].yyv.node);
	} break;
case 75:
#line	395	"cc.y"
{
		yyval.node = new(OCASE, yypt[-1].yyv.node, Z);
	} break;
case 76:
#line	399	"cc.y"
{
		yyval.node = new(OCASE, Z, Z);
	} break;
case 77:
#line	403	"cc.y"
{
		yyval.node = new(OLABEL, dcllabel(yypt[-1].yyv.sym, 1), Z);
	} break;
case 78:
#line	409	"cc.y"
{
		yyval.node = Z;
	} break;
case 80:
#line	414	"cc.y"
{
		yyval.node = new(OLIST, yypt[-1].yyv.node, yypt[-0].yyv.node);
	} break;
case 82:
#line	421	"cc.y"
{
		yyval.node = yypt[-0].yyv.node;
	} break;
case 84:
#line	427	"cc.y"
{
		markdcl();
	} break;
case 85:
#line	431	"cc.y"
{
		yyval.node = revertdcl();
		if(yyval.node)
			yyval.node = new(OLIST, yyval.node, yypt[-0].yyv.node);
		else
			yyval.node = yypt[-0].yyv.node;
	} break;
Exemple #16
0
const char *ExtractOuterCf3VarString(const char *str, char *substr)
  /* Should only by applied on str[0] == '$' */
{
    const char *sp;
    int dollar = false;
    int bracks = 0, onebrack = false;

    CfDebug("ExtractOuterVarString(\"%s\") - syntax verify\n", str);

    memset(substr, 0, CF_BUFSIZE);

    for (sp = str; *sp != '\0'; sp++)   /* check for varitems */
    {
        switch (*sp)
        {
        case '$':
            dollar = true;
            switch (*(sp + 1))
            {
            case '(':
            case '{':
                break;
            default:
                /* Stray dollar not a variable */
                return NULL;
            }
            break;
        case '(':
        case '{':
            bracks++;
            onebrack = true;
            break;
        case ')':
        case '}':
            bracks--;
            break;
        }

        if (dollar && (bracks == 0) && onebrack)
        {
            strncpy(substr, str, sp - str + 1);
            CfDebug("Extracted outer variable |%s|\n", substr);
            return substr;
        }
    }

    if (dollar == false)
    {
        return str;             /* This is not a variable */
    }

    if (bracks != 0)
    {
        char output[CF_BUFSIZE];

        snprintf(output, CF_BUFSIZE, "Broken variable syntax or bracket mismatch in - outer (%s/%s)", str, substr);
        yyerror(output);
        return NULL;
    }

/* Return pointer to first position in string (shouldn't happen)
   as long as we only call this function from the first $ position */

    return str;
}
Exemple #17
0
static OBJECT_FILE *object_open( const char *file_name )
{
    OBJECT_FILE *file;
    Elf_Scn *section;
    Elf_Data *symtab;
    Elf32_Shdr *shdr;
    int compare;

    // search for the file in the list of already open objects
    for (file = objects ; file ; file = file->next_object)
    {
        compare = strcmp( file_name, file->name );
        if ( compare == 0 ) // if we found it
        {
            return file;
        }
        else if ( compare < 0 )  // if we didn't find it
        {
            break;
        }
    }

    // try to add a new file to the list of open objects
    file = (OBJECT_FILE *)malloc( sizeof(OBJECT_FILE) );
    assert(file);
    if ( file )
    {
        memset( file, 0, sizeof(*file) );
        if ((file->fd = open(file_name, O_RDONLY | O_BINARY)) != -1)
        {
            file->elf = elf_begin(file->fd, ELF_C_READ, NULL);
            if (file->elf)
            {
                file->ehdr = elf32_getehdr(file->elf);
                if (file->ehdr)
                {
                    if ( file->ehdr->e_machine == out_file_machine )
                    {
                        Elf_Data *string_data;
                        OBJECT_FILE **scan;
                        int compare;

                        exec_getsection( file->elf, file->ehdr->e_shstrndx,
                                         NULL, &string_data );
                        file->strings = (char *)string_data->d_buf;
                        file->name = strdup( file_name );

                        section = NULL;
                        while ((section =
                                elf_nextscn(file->elf, section)) != 0)
                        {
                            shdr = elf32_getshdr(section);
                            elfcheck( shdr != NULL );
                            if (shdr->sh_type == SHT_SYMTAB)
                            {
                                symtab = exec_getdata(section);
                                file->symbols = symtab->d_buf;
                                file->symbol_count = symtab->d_size /
                                    sizeof(Elf32_Sym);
                                file->first_global = shdr->sh_info;
                                file->string_index = shdr->sh_link;
                                if ( file->symbol_count > max_symbols )
                                {
                                    max_symbols = file->symbol_count;
                                }
                                break;
                            }
                        }

                        // ordered insert into the file list
                        assert( file->name );
                        for ( scan = &objects ; *scan ;
                              scan = &(*scan)->next_object )
                        {
                            compare = strcmp(file_name, (*scan)->name );
                            // if this file already exists we should have found
                            // it instead of creating it
                            assert( compare != 0 );
                            if (compare < 0)
                            {
                                break;
                            }
                        }
                        file->next_object = *scan;
                        *scan = file;
                        return file;
                    }
                    else
                    {
                        yyerror(
                            "Input file machine type doesn't match architecture" );
                    }
                }
                else
                {
                    yyerror( "File %s is not a valid ELF file: %s",
                             file_name, elf_errmsg(-1) );
                }
                elf_end(file->elf);
            }
            else
            {
                yyerror( "Elf_begin on %s failed: %s",
                         file_name, elf_errmsg(-1) );
            }
            close( file->fd );
        }
        else
        {
            yyerror( "File %s not found", file_name );
        }
        free( file );
        file = NULL;
    }
    return file;
}
Exemple #18
0
bool yyparse( void )
{
  short yypnum;
  short yyi, yyk, yylhs, yyaction;
  short yytoken;
  short yys[MAXDEPTH], *yysp;
  YYSTYPE yyv[MAXDEPTH], *yyvp;
  short yyerrflag;

  yyerrflag = 0;
  yyaction = 0;
  yysp = yys;
  yyvp = yyv;
  *yysp = YYSTART;
  yytoken = yylex();
  for(;;){
yynewact:
      yyk = *yysp;
      while( (yyi = yyk + yytoken) < 0 || yyi >= YYUSED || yychktab[yyi] != yytoken )
          if( (yyi = yyk + YYPTOKEN) < 0 || yyi >= YYUSED || yychktab[yyi] != YYPTOKEN )
              goto yycheck1;
          else
              yyk = yyacttab[yyi];
      yyaction = yyacttab[yyi];
      if( yyaction == YYNOACTION ){
yycheck1:
          yyk = *yysp;
          while( (yyi = yyk + YYDTOKEN) < 0 || yyi >= YYUSED || yychktab[yyi] != YYDTOKEN )
              if( (yyi = yyk + YYPTOKEN) < 0 || yyi >= YYUSED || yychktab[yyi] != YYPTOKEN )
                  goto yycheck2;
              else
                  yyk = yyacttab[yyi];
          yyaction = yyacttab[yyi];
          if( yyaction == YYNOACTION ){
yycheck2:
              switch( yyerrflag ){
                case 0:
                  yyerror( "syntax error" );
                  yyerrlab:
                case 1:
                case 2:
                  yyerrflag = 3;
                  while( yysp >= yys ){
                      yyk = *yysp;
                      while( (yyi = yyk + YYETOKEN) < 0 || yyi >= YYUSED || yychktab[yyi] != YYETOKEN )
                          if( (yyi = yyk + YYPTOKEN) < 0 || yyi >= YYUSED || yychktab[yyi] != YYPTOKEN )
                              goto continu;
                          else
                              yyk = yyacttab[yyi];
                      yyaction = yyacttab[yyi];
                      if( yyaction < YYUSED ){
                          *++yysp = yyaction;
                          ++yyvp;
                          goto yynewact;
                      };
                      continu:;
                      --yysp;
                      --yyvp;
                  };
                  YYABORT;
                case 3:
                  if( yytoken == 0 ) /* EOF token */
                      YYABORT;
                  yytoken = yylex();
                  goto yynewact;
              };
          };
      };
      if( yyaction < YYUSED ){
          if( yyaction == YYSTOP ){
              YYACCEPT;
          } else {
              *++yysp = yyaction;
              *++yyvp = yylval;
              if( yyerrflag )
                  --yyerrflag;
              yytoken = yylex();
          };
      } else {
          yypnum = yyaction - YYUSED;
          yyi = yyplentab[yypnum];
          yysp -= yyi;
          yyvp -= yyi;
          yylhs = yyplhstab[yypnum];
          if( yysp < yys ){
              printf( "stack underflow\n" );
              YYABORT;
          };
          yyk = *yysp;
          while( (yyi = yyk + yylhs) < 0 || yyi >= YYUSED || yychktab[yyi] != yylhs ){
              if( (yyi = yyk + YYPTOKEN) < 0 || yyi >= YYUSED || yychktab[yyi] != YYPTOKEN ){
                  printf( "missing nonterminal\n" );
                  YYABORT;
              };
              yyk = yyacttab[yyi];
          };
          *++yysp = yyacttab[yyi];
          ++yyvp;
#ifdef AS_DEBUG_DUMP
          dump_rule( yypnum );
#endif
          switch( yypnum ){

            default:
              yyval = yyvp[0];
          };
          *yyvp = yyval;
      };
  };
}
Exemple #19
0
static void fixup_symbols( void )
{
    bbtree_node_t *parent;
    OBJECT_FILE *file;
    Elf_Scn *section;
    Elf32_Shdr *shdr;
    Elf32_Sym *symbol;
    global_t *global_sym;
    int i;
    int compare;
    char *sym_name;

    file = objects;
    while (file)
    {
        section = NULL;
        while ((section = elf_nextscn(file->elf, section)) != 0)
        {
            shdr = elf32_getshdr(section);
            elfcheck( shdr != NULL );
            if ( (shdr->sh_type == SHT_PROGBITS ||
                  shdr->sh_type == SHT_NOBITS) &&
                 (shdr->sh_flags & SHF_REFERENCED) == 0)
            {
                yyerror( "Section %s in file %s is not referenced\n",
                         file->strings + shdr->sh_name, file->name );
            }
        }
        symbol = file->symbols + 1;
        for ( i = 1 ; i < file->symbol_count ; ++i )
        {
            sym_name = elf_strptr( file->elf, file->string_index,
                                   symbol->st_name);
            if (symbol->st_shndx != SHN_UNDEF)
            {
                exec_getsection( file->elf, symbol->st_shndx,
                                 &shdr, NULL );
                symbol->st_value += shdr->sh_addr;
                if (i >= file->first_global)
                {
                    parent = bbtree_preinsert( &globals, sym_name,
                                               &compare );
                    if (!parent || compare != 0)
                    {
                        global_sym = (global_t *)malloc(sizeof(*global_sym));
                        if (global_sym)
                        {
                            global_sym->file = file;
                            global_sym->name = sym_name;
                            global_sym->symbol = symbol;
                            bbtree_insert( &globals, parent, &global_sym->node,
                                           compare );
                        }
                        else
                        {
                            yyerror( "Failed to allocate memory\n" );
                        }

                    }
                    else
                    {
                        yyerror( "Global symbol \"%s\" multiply defined\n",
                                 sym_name );
                    }
                }
            }
            else if (i < file->first_global)
            {
                yyerror( "Symbol \"%s\" is undefined but local\n",
                         sym_name );
            }
            ++symbol;
        }
        file = file->next_object;
    }
}
Exemple #20
0
int StartVSM(int StartAddr, int TraceSW)         /* Start VSM */
{
  int addr, op;

  Pctr = StartAddr;                              /* Set Pctr */
  SP = Freg = 0;                                 /* Set register flag */
  while (1) {
    if (SP >= STACK_SIZE || SP < 0) {            /* check the range of stack pointer */
      fprintf(stderr, "Illegal Stack pointer %d\n", SP);
      return -1; }
    op   = Iseg[Pctr].Op;                        /* fetch instruction */
    addr = Iseg[Pctr].Addr;                      /* calculate effective address */
    if (Iseg[Pctr++].Reg & FP)                   /* FP register modification */
      addr += Freg;                              /* add FP */
    InsCount++;                                  /* Increment the number of instructions */
    if (SP > MaxSD) MaxSD = SP;                  /* check the max SP value */
    if (TraceSW) {                               /* if trace flag is on, make trace */
      PrintIns(Pctr-1);
      printf("%15d %5d %12d\n", addr, SP, Stack[SP]); }
    switch (op) {                                /* execute each instruction */
      case NOP:                                              continue;
      case ASSGN:  addr = Stack[--SP];
                   Dseg[addr] = Stack[SP] = Stack[SP+1];     continue;
      case ADD:    BINOP(+);                                 continue;
      case SUB:    BINOP(-);                                 continue;
      case MUL:    BINOP(*);                                 continue;
      case DIV:    if (Stack[SP] == 0) {
                     yyerror("Zero divider detected"); return -2; }
                   BINOP(/);                                 continue;
      case MOD:    if (Stack[SP] == 0) {
                     yyerror("Zero divider detected"); return -2; }
                   BINOP(%);                                 continue;
      case CSIGN:  Stack[SP] = -Stack[SP];                   continue;
      case AND:    BINOP(&&);                                continue;
      case OR:     BINOP(||);                                continue;
      case NOT:    Stack[SP] = !Stack[SP];                   continue;
      case COMP:   Stack[SP-1] = Stack[SP-1] > Stack[SP] ? 1 :
                                 Stack[SP-1] < Stack[SP] ? -1 : 0;
                   SP--;                                     continue;
      case COPY:   ++SP; Stack[SP] = Stack[SP-1];            continue;
      case PUSH:   Stack[++SP] = Dseg[addr];                 continue;
      case PUSHI:  Stack[++SP] = addr;                       continue;
      case REMOVE: --SP;                                     continue;
      case POP:    Dseg[addr] = Stack[SP--];                 continue;
      case INC:    Stack[SP] = ++Stack[SP];                  continue;
      case DEC:    Stack[SP] = --Stack[SP];                  continue;
      case SETFR:  Freg = addr;                              continue;
      case INCFR : if ((Freg += addr) >= DSEG_SIZE) {
                     printf("Freg overflow at loc. %d\n", Pctr-1);
                     return -3; }                            continue;
      case DECFR : Freg -= addr;
                   if (Freg < MinFR) MinFR = Freg;           continue;
      case JUMP:   Pctr = addr;           continue;
      case BLT:    if (Stack[SP--] <  0) Pctr = addr;        continue; 
      case BLE:    if (Stack[SP--] <= 0) Pctr = addr;        continue; 
      case BEQ:    if (Stack[SP--] == 0) Pctr = addr;        continue; 
      case BNE:    if (Stack[SP--] != 0) Pctr = addr;        continue; 
      case BGE:    if (Stack[SP--] >= 0) Pctr = addr;        continue; 
      case BGT:    if (Stack[SP--] >  0) Pctr = addr;        continue; 
      case CALL:   Stack[++SP] = Pctr; Pctr = addr; CallC++; continue;
      case RET:    Pctr = Stack[SP--];                       continue;
      case HALT:                                             return 0;
      case INPUT:  scanf("%d", &Dseg[Stack[SP--]]);          continue;
      case OUTPUT: printf("%15d\n", Stack[SP--]);            continue;
      default:
        printf("Illegal Op. code at location %d\n", Pctr);   return -4;
      }
  }
}
Exemple #21
0
int main(int argc, char *argv[]) {
	int c, i;
	Nonterm p;
	
	for (i = 1; i < argc; i++)
		if (strcmp(argv[i], "-T") == 0)
			Tflag = 1;
		else if (strncmp(argv[i], "-p", 2) == 0 && argv[i][2])
			prefix = &argv[i][2];
		else if (strncmp(argv[i], "-p", 2) == 0 && i + 1 < argc)
			prefix = argv[++i];
		else if (*argv[i] == '-' && argv[i][1]) {
			yyerror("usage: %s [-T | -p prefix]... [ [ input ] output ] \n",
				argv[0]);
			exit(1);
		} else if (infp == NULL) {
			if (strcmp(argv[i], "-") == 0)
				infp = stdin;
			else if ((infp = fopen(argv[i], "r")) == NULL) {
				yyerror("%s: can't read `%s'\n", argv[0], argv[i]);
				exit(1);
			}
		} else if (outfp == NULL) {
			if (strcmp(argv[i], "-") == 0)
				outfp = stdout;
			if ((outfp = fopen(argv[i], "w")) == NULL) {
				yyerror("%s: can't write `%s'\n", argv[0], argv[i]);
				exit(1);
			}
		}
	if (infp == NULL)
		infp = stdin;
	if (outfp == NULL)
		outfp = stdout;
	yyparse();
	if (start)
		ckreach(start);
	for (p = nts; p; p = p->link) {
		if (p->rules == NULL)
			yyerror("undefined nonterminal `%s'\n", p->name);
		if (!p->reached)
			yyerror("can't reach nonterminal `%s'\n", p->name);
	}
	emitheader();
	emitdefs(nts, ntnumber);
	emitstruct(nts, ntnumber);
	emitnts(rules, nrules);
	emitstring(rules);
	emitrule(nts);
	emitclosure(nts);
	if (start)
		emitlabel(terms, start, ntnumber);
	emitkids(rules, nrules);
	if (!feof(infp))
		while ((c = getc(infp)) != EOF)
			putc(c, outfp);
	while (memlist) {	/* for purify */
		struct block *q = memlist->link;
		free(memlist);
		memlist = q;
	}
	return errcnt > 0;
}
Exemple #22
0
int
assemble(char *file)
{
	char ofile[100], incfile[20], *p;
	int i, of;

	strcpy(ofile, file);
	p = utfrrune(ofile, pathchar());
	if(p) {
		include[0] = ofile;
		*p++ = 0;
	} else
		p = ofile;
	if(outfile == 0) {
		outfile = p;
		if(outfile){
			p = utfrrune(outfile, '.');
			if(p)
				if(p[1] == 's' && p[2] == 0)
					p[0] = 0;
			p = utfrune(outfile, 0);
			p[0] = '.';
			p[1] = thechar;
			p[2] = 0;
		} else
			outfile = "/dev/null";
	}
	p = getenv("INCLUDE");
	if(p) {
		setinclude(p);
	} else {
		if(systemtype(Plan9)) {
			sprint(incfile,"/%s/include", thestring);
			setinclude(strdup(incfile));
		}
	}

	of = create(outfile, OWRITE, 0664);
	if(of < 0) {
		yyerror("%ca: cannot create %s", thechar, outfile);
		errorexit();
	}
	Binit(&obuf, of, OWRITE);

	pass = 1;
	pinit(file);

	Bprint(&obuf, "%s\n", thestring);

	for(i=0; i<nDlist; i++)
		dodefine(Dlist[i]);
	yyparse();
	if(nerrors) {
		cclean();
		return nerrors;
	}

	Bprint(&obuf, "\n!\n");

	pass = 2;
	outhist();
	pinit(file);
	for(i=0; i<nDlist; i++)
		dodefine(Dlist[i]);
	yyparse();
	cclean();
	return nerrors;
}
Exemple #23
0
void yyserror(const char *str, char *other)
{
    sprintf(errmsg, str, other);
    yyerror(errmsg);
}
Exemple #24
0
int
main(int argc, char **argv)
{
   int /*ch, */ i, ii, ret, err_flag = 0;

   clock_t beg, end, Beg, End;

   int files = 0;

   struct tms ts;

   char buf[256];

   char *e;

   prgname = strrchr(argv[0], '/');

   if (prgname)
      prgname++;
   else
      prgname = argv[0];

   e = getenv("CLIP_HOSTCS");
   if (e && *e)
   {
      sourceCharset = targetCharset = strdup(e);
   }
   else if (!e)
   {
      e = getenv("CLIP_LANG");
      if (e == NULL)
	 e = getenv("LANG");
      if (!e || !*e || !strcmp(e, "C"))
	 e = getenv("LC_MESSAGES");
      if (!e || !*e || !strcmp(e, "C"))
	 e = getenv("LC_ALL");
      if (e && *e)
      {
	 char *s = strrchr(e, '.');

	 if (s)
	 {
	    snprintf(buf, sizeof(buf), "%s", s + 1);
	    for (s = buf; *s; s++)
	       *s = tolower(*s);
	    sourceCharset = targetCharset = strdup(buf);
	 }
      }
   }

   {
      e = getenv("CLIP_LANG");
      if (e == NULL)
	 e = getenv("LANG");
      if (!e || !*e || !strcmp(e, "C"))
	 e = getenv("LC_MESSAGES");
      if (!e || !*e || !strcmp(e, "C"))
	 e = getenv("LC_ALL");
      if (e && *e)
      {
	 char *s = strrchr(e, '.');

	 if (s)
	 {
	    snprintf(buf, sizeof(buf), "%s", s + 1);
	    for (s = buf; *s; s++)
	       *s = tolower(*s);
	    out_charset = strdup(buf);
	 }
      }
   }

   {
      char *locale;

      locale = getenv("CLIP_LANG");
      if (!locale || !*locale)
	 locale = getenv("LANG");
      /*if (locale && *locale &&
         strcasecmp(locale, "C") && strcasecmp(locale, "POSIX")) */
      /*
         setlocale(LC_ALL, locale);
       */
   }

   if (!sourceCharset)
      sourceCharset = targetCharset = strdup("c");

   getEnvironment();

   init_Coll(&includePaths, NULL, NULL);
   init_Coll(&lib_dirs, NULL, NULL);
   init_Coll(&arglibs, NULL, NULL);

#if 1
   insert_Coll(&includePaths, ".");
   snprintf(buf, sizeof(buf), "%s/include", CLIPROOT);
   insert_Coll(&includePaths, strdup(buf));
#ifdef STD_LIBDIR
   snprintf(buf, sizeof(buf), STD_LIB_DIR);
   insert_Coll(&lib_dirs, strdup(buf));
#endif
   snprintf(buf, sizeof(buf), "%s/lib", CLIPROOT);
   insert_Coll(&lib_dirs, strdup(buf));
#endif
   init_Coll(&predefines, NULL, NULL);
   init_Coll(&poName, NULL, NULL);
   init_Coll(&paName, NULL, NULL);
   init_Coll(&include_files, NULL, NULL);

   snprintf(buf, sizeof(buf), "__CLIP__=\"%s\"", CLIP_VERSION);
   append_Coll(&predefines, strdup(buf));

   init_module();

   {
      char buf[256], *s;

      s = getenv("HOME");
      if (s && *s)
      {
	 snprintf(buf, sizeof(buf), "%s/.cliprc", s);
	 getrc(buf);
      }

   }

   getrc(".cliprc");

   {
      char buf[256], *s;

      DIR *dp;

      s = CLIPROOT;
      if (s && *s)
      {
	 snprintf(buf, sizeof(buf), "%s/.cliprc", s);
	 getrc(buf);
      }

      snprintf(buf, sizeof(buf), "%s/cliprc", CLIPROOT);
      dp = opendir(buf);
      if (dp)
      {
	 struct dirent *ep;

	 struct stat st;

	 Coll files;

	 int i;

	 init_Coll(&files, free, strcmp);
	 while ((ep = readdir(dp)))
	 {
	    snprintf(buf, sizeof(buf), "%s/cliprc/%s", CLIPROOT, ep->d_name);
	    if (stat(buf, &st))
	       continue;
	    if (!S_ISREG(st.st_mode))
	       continue;
	    if (access(buf, R_OK))
	       continue;
	    insert_Coll(&files, strdup(buf));
	 }
	 closedir(dp);

	 for (i = 0; i < files.count_of_Coll; i++)
	 {
		 char *name = (char *) files.items_of_Coll[i];

	    getrc(name);
	 }

	 destroy_Coll(&files);
      }
   }

   argc--;
   argv++;
   get_opt(argc, argv);

   argc -= optind;
   argv += optind;

   if (err_flag)
      return 1;

#if 0
   insert_Coll(&includePaths, ".");
   snprintf(buf, sizeof(buf), "%s/include", CLIPROOT);
   insert_Coll(&includePaths, strdup(buf));
#ifdef STD_LIBDIR
   snprintf(buf, sizeof(buf), STD_LIBDIR);
   insert_Coll(&lib_dirs, strdup(buf));
#endif
   snprintf(buf, sizeof(buf), "%s/lib", CLIPROOT);
   insert_Coll(&lib_dirs, strdup(buf));
#endif

   if (syntax_tree_flag)
   {
      write_obj_flag = 0;
      codegen_flag = 1;
      compile_flag = 0;
      pcode_flag = 0;
      pc_flag = 0;
      asm_flag = 0;
      exec_flag = 0;
   }

   if (!write_obj_flag)
   {
      /*codegen_flag = 0; */
      compile_flag = 0;
   }
   if (preproc_flag)
   {
      write_obj_flag = 0;
      codegen_flag = 0;
      syntax_tree_flag = 0;
      compile_flag = 0;
      exec_flag = 0;
      pcode_flag = 0;
      pc_flag = 0;
      asm_flag = 0;
      shared_flag = 0;
   }

   if (pcode_flag)
   {
      pc_flag = 0;
      asm_flag = 0;
      shared_flag = 0;
   }

   if (pc_flag)
   {
      pcode_flag = 1;
#ifdef USE_AS
      if (use_asm)
	 asm_flag = 1;
      else
	 asm_flag = 0;
#endif
   }

   if (xpc_flag)
   {
      pcode_flag = 1;
      pc_flag = 1;
#ifdef USE_AS
      if (use_asm)
	 asm_flag = 0;
      else
	 asm_flag = 1;
#endif
   }

#if 0
   if (shared_flag && pcode_flag)
   {
      v_printf(0, "conflict between -s and -p flags\n");
      exit(1);
   }
#endif

   if (pcode_flag && c_flag)
   {
      v_printf(0, "conflict between -c and -p flags\n");
      exit(1);
   }

   /*if ( exec_flag && !main_flag && !shared_flag)
      {
      v_printf(0, "-e(xec) flag without -M(ain) or -s(hared) flags\n");
      exit(2);
      } */

   if (pcode_flag)
   {
      compile_flag = 0;
   }

   if (nomain_flag && main_flag)
   {
      v_printf(0, "conflict between -n and -m flags\n");
      exit(1);
   }

   if (!exec_flag && oname)
   {
      char *e;

      if (oname[0] == '/')
	 snprintf(buf, sizeof(buf), "%s", oname);
      else
	 snprintf(buf, sizeof(buf), "%s%s%s", outdir ? outdir : "", outdir ? "/" : "", oname);
      e = strrchr(buf, '/');
      if (e)
      {
	 *e = 0;
	 outdir = strdup(buf);
      }
   }

   if (!outdir)
      outdir = ".";

   if (outdir)
   {
      char cdir[256];

      getcwd(cdir, sizeof(cdir));

      if (!chdir(outdir))
      {
	 getcwd(buf, sizeof(buf));
	 outdir = strdup(buf);
	 chdir(cdir);
      }
      else
      {
	 yyerror("cannot change to output dir '%s': %s", outdir, strerror(errno));
	 exit(1);
      }
   }

   if (!preproc_flag)
   {
      v_printf(2, "set source charset to %s\n", sourceCharset);
      v_printf(2, "set target charset to %s\n", targetCharset);
   }

   init_lex();
   init_parser();

   if (argc < 1)
      ii = -1;
   else
      ii = 0;

   Beg = times(&ts);
   if (argc > 0)
   {
      for (i = 0; i < argc; i++)
      {
	 char *e;

	 e = argv[i];
	 if (e[0] == '-' && e[1] == 'L')
	 {
	    insert_Coll(&lib_dirs, strdup(e + 2));
	    continue;
	 }
	 e = strrchr(argv[i], '.');
	 if (!e)
	 {
	    e = argv[i];
	    if (e[0] == '-' && e[1] == 'l')
	       /*append_Coll(&arglibs, strdup(e+2)) */ ;
	    else
	       yyerror("unknown file type '' file '%s'", argv[i]);
	    continue;
	 }
	 else if (!strcasecmp(e, ".po"))
	    insert_Coll(&poName, strdup(argv[i]));
	 else if (!strcasecmp(e, ".pa"))
	    insert_Coll(&paName, strdup(argv[i]));
	 else if (strcasecmp(e, ".prg") && strcasecmp(e, ".c") && strcasecmp(e, ".cc") && strcasecmp(e, OBJSUF) && strcasecmp(e, SOBJSUF) && strcasecmp(e, ".a") && strcasecmp(e, ".lib"))
	 {
	    /*yywarning("unknown file type '%s' file '%s'", e, argv[i]); */
	    continue;
	 }
      }
   }

   for (; clic_errorcount == 0 && ii < argc; ii++)
   {
      ++files;
      if (ii < 0)
      {
	 v_printf(1, "no input files, so use stdin; -h will help\n");
	 fflush(stderr);
	 set_locale_name("stdin");
	 ret = clic_parse("stdin", stdin);
	 add_name("stdin");
      }
      else
      {
	 char *e;

	 e = strrchr(argv[ii], '.');
	 add_name(argv[ii]);

	 if (!e)
	    continue;
	 else if (!strcasecmp(e, ".c") || !strcasecmp(e, ".cc") || !strcasecmp(e, ".cpp"))
	 {
	    if (!preproc_flag)
	    {
	       v_printf(1, "process file '%s' ..", argv[ii]);
	       v_neednl = 1;
	    }

	    beg = times(&ts);
	    compile_CFile(argv[ii]);
	    end = times(&ts);

	    if (!preproc_flag)
	    {
	       v_neednl = 0;
	       if (clic_errorcount == 0)
		  v_printf(1, ".. done, %s\n", diff_clock(beg, end));
	       else
		  pr_errorcount(1);
	    }
	    continue;
	 }
	 else if (strcasecmp(e, ".prg"))
	 {
	    continue;
	 }

	 if (ii > 0)
	    main_flag = 0;

	 if (!preproc_flag)
	 {
	    v_printf(1, "parsing file '%s' ..", argv[ii]);
	    v_neednl = 1;
	 }
	 beg = times(&ts);
	 set_locale_name(argv[ii]);
	 ret = clic_parse(argv[ii], 0);
	 end = times(&ts);

	 if (!preproc_flag)
	 {
	    v_neednl = 0;
	    if (clic_errorcount == 0)
	       v_printf(1, ".. done (%d/%d %s, %d %s, %s)\n",
			clic_line, all_lines, _clic_ngettext("line", "lines", clic_line), clic_warncount, _clic_ngettext("warning", "warnings", clic_warncount), diff_clock(beg, end));
	    else
	       vr_printf(1, "%d %s, %d %s\n", clic_errorcount, _clic_ngettext("error", "errors", clic_errorcount), clic_warncount, _clic_ngettext("warning", "warnings", clic_warncount));
	 }
      }
      if (ret)
	 break;

      if (clic_errorcount == 0 && codegen_flag)
      {
	 v_printf(2, "codegen file '%s' ..", curFile->name_of_File);
	 v_neednl = 1;
	 beg = times(&ts);
	 codegen_File(curFile);
	 end = times(&ts);
	 v_neednl = 0;
	 if (clic_errorcount == 0)
	    v_printf(2, ".. done, %s\n", diff_clock(beg, end));
	 else
	    pr_errorcount(2);
      }
      if (clic_errorcount == 0 && syntax_tree_flag)
      {
	 print_File(curFile);
      }
      if (clic_errorcount == 0 && write_obj_flag)
      {
	 if (pcode_flag)
	 {
	    long len;

	    v_printf(1, "writing file '%s' ..", curFile->s_cname_of_File);
	    v_neednl = 1;
	    beg = times(&ts);
	    write_OFile(curFile, &len);
	    write_names(curFile);
	    end = times(&ts);
	    v_neednl = 0;
	    if (clic_errorcount == 0)
	       v_printf(1, ".. done, %ld %s ,%s\n", len, _clic_ngettext("byte", "bytes", len), diff_clock(beg, end));
	    else
	       pr_errorcount(1);
	 }
	 else
	 {
	    v_printf(2, "writing file '%s' ..", curFile->s_cname_of_File);
	    v_neednl = 1;
	    write_File(curFile);
	    write_names(curFile);
	    v_neednl = 0;
	    if (clic_errorcount == 0)
	       v_printf(2, ".. done\n");
	    else
	       pr_errorcount(2);
	 }
      }

      if (clic_errorcount == 0 && (compile_flag || pc_flag))
      {
	 if (ii)
	    main_flag = 0;
	 v_printf(1, "compile file '%s' ..", curFile->s_cname_of_File);
	 v_neednl = 1;
	 beg = times(&ts);
	 compile_File(curFile->cname_of_File);
	 end = times(&ts);
	 v_neednl = 0;
	 if (clic_errorcount == 0)
	    v_printf(1, ".. done, %s\n", diff_clock(beg, end));
	 else
	    pr_errorcount(1);

	 if (clic_errorcount == 0 && shared_flag && !exec_flag)
	 {
	    v_printf(1, "make shared object '%s' ..", curFile->s_cname_of_File);
	    v_neednl = 1;
	    beg = times(&ts);
	    share_File(curFile->cname_of_File);
	    end = times(&ts);
	    v_neednl = 0;
	    if (clic_errorcount == 0)
	       v_printf(1, ".. done, %s\n", diff_clock(beg, end));
	    else
	       pr_errorcount(1);

	 }
      }

      if (ii < 0)
	 break;

      delete_File(curFile);
      curFile = NULL;
   }

   if (clic_errorcount == 0 && exec_flag)
   {
      char cmd[1024 * 8], *e;

      char cfuncname[256], ofuncname[256];

      char *libroot;

      int i;

      Coll ex, nm;

      init_Coll(&ex, free, strcasecmp);
      init_Coll(&nm, free, strcasecmp);
#ifdef STD_LIBDIR
      libroot = 0;
#else
      libroot = CLIPROOT;
#endif

      ++files;
#ifdef STD_LIBDIR
      if (eshared_flag || shared_flag)
      {
	 snprintf(cmd, sizeof(cmd), "-lclip");
	 add_name(cmd);
      }
      else
#endif
      {
	 e = (eshared_flag || shared_flag) ? CLIPSLIB : CLIPLIB;
	 lib_name(cmd, sizeof(cmd), libroot, "lib", e, strlen(e));
	 add_name(cmd);
      }
      for (e = CLIPLIBS; *e;)
      {
	 int l;

	 l = strspn(e, " \t");
	 e += l;
	 l = strcspn(e, " \t");
	 if (!l)
	    break;
	 lib_name(cmd, sizeof(cmd), libroot, "lib", e, l);
	 add_name(cmd);
	 e += l;
      }
      for (e = ADDLIBS; *e;)
      {
	 int l;

	 l = strspn(e, " \t");
	 e += l;
	 l = strcspn(e, " \t");
	 if (!l)
	    break;
	 memcpy(cmd, e, l);
	 cmd[l] = 0;
	 add_name(cmd);
	 e += l;
      }
      add_name(MATHLIB);
      add_name(DLLIB);

      /* generate _cfunctions */
      if (asm_flag)
	 sprintf(cfuncname, "%s_ref.s", oname);
      else
	 sprintf(cfuncname, "%s_ref.c", oname);
      sprintf(ofuncname, "%s_ref.o", oname);
      v_printf(1, "generate reference file '%s' ..", cfuncname);
      v_neednl = 1;
      beg = times(&ts);
      write_Cfunc(cfuncname, onum, ovect, &ex, &nm);
      check_names(&ex, &nm);
      end = times(&ts);
      v_neednl = 0;
      if (clic_errorcount == 0)
	 v_printf(1, ".. done, %s\n", diff_clock(beg, end));
      else
	 pr_errorcount(1);
      if (clic_errorcount)
	 goto end;

      v_printf(1, "compile file '%s' ..", cfuncname);
      v_neednl = 1;
      beg = times(&ts);
      compile_File(cfuncname);
      end = times(&ts);
      v_neednl = 0;
      if (clic_errorcount == 0)
	 v_printf(1, ".. done, %s\n", diff_clock(beg, end));
      else
	 pr_errorcount(1);

#ifdef USE_LD
      if (use_asm && (shared_flag || eshared_flag))
      {
	 int ll;

	 const char *ld_prg, *ld_end;

	 if (shared_flag || eshared_flag)
	 {
	    ld_prg = LD_PRG;
	    ld_end = LD_END;
	 }
	 else
	 {
	    ld_prg = LDS_PRG;
	    ld_end = LDS_END;
	 }

	 snprintf(cmd, sizeof(cmd), "%s", ld_prg);
	 ll = strlen(cmd);
	 for (e = cmd + ll, i = 0; i < lib_dirs.count_of_Coll; ++i)
	 {
		 snprintf(e, sizeof(cmd) - ll, " -L%s", (char *) lib_dirs.items_of_Coll[i]);
	    ll = strlen(cmd);
	    e = cmd + ll;
	 }
	 ll = strlen(cmd);
	 snprintf(cmd + ll, sizeof(cmd) - ll, " %s %s %s -o %s", optLevel ? COPT : "", genDebug ? CDBG : "", ofuncname, oname);
	 ll = strlen(cmd);
	 for (e = cmd + ll, i = 0; i < onum; ++i)
	 {
	    snprintf(e, sizeof(cmd) - ll, " %s", ovect[i]);
	    ll = strlen(cmd);
	    e = cmd + ll;
	 }
	 ll = strlen(cmd);
	 snprintf(cmd + ll, sizeof(cmd) - ll, " %s", ld_end);
      }
      else
#endif
      {
	 sprintf(cmd, "%s", CC);
	 for (e = cmd + strlen(cmd), i = 0; i < includePaths.count_of_Coll; ++i)
	 {
		 sprintf(e, " %s %s", INCLUDE_FLAG, (char *) includePaths.items_of_Coll[i]);
	    e = cmd + strlen(cmd);
	 }

	 for (e = cmd + strlen(cmd), i = 0; i < lib_dirs.count_of_Coll; ++i)
	 {
		 sprintf(e, " -L%s", (char *) lib_dirs.items_of_Coll[i]);
	    e = cmd + strlen(cmd);
	 }

	 sprintf(cmd + strlen(cmd), " %s %s %s %s %s %s %s", optLevel ? COPT : "", genDebug ? CDBG : "", CFLAGS, ADDCFLAGS, ofuncname, OUT_FLAG, oname);
	 for (e = cmd + strlen(cmd), i = 0; i < onum; ++i)
	 {
	    sprintf(e, " %s", ovect[i]);
	    e = cmd + strlen(cmd);
	 }
      }

      v_printf(1, "make file '%s' ..", oname);
      v_neednl = 1;
      beg = times(&ts);
      v_printf(2, "%s\n", cmd);
      if (system(cmd))
	 yyerror("C level error in command: %s", cmd);
      else if (rmc_flag)
      {
	 unlink(cfuncname);
	 unlink(ofuncname);
      }

      end = times(&ts);
      v_neednl = 0;
      if (clic_errorcount == 0)
	 v_printf(1, ".. done, %s\n", diff_clock(beg, end));
      else
	 pr_errorcount(1);
   }

 end:
   End = times(&ts);

   resume_parser();
   resume_lex();
   resume_locale();

   if (!preproc_flag)
      v_printf(1, "clip: %d %s, %s\n", files, _clic_ngettext("file", "files", files), diff_clock(Beg, End));
   return clic_errorcount == 0 ? 0 : 1;
}
Exemple #25
0
data eval_expr(node expr, symrec ** symTable,list * routineList){
  data res;
  switch (expr.operator) {
    case SEMICOLON:
      {
        //c'è sempre uno statement da valutare
        //valuto il primo
        eval(expr.op[0],symTable,routineList);
        if(expr.noperands>1){
          //valuto il secondo, non è possibile per la struttura del parser averne più di due
          return eval(expr.op[1], symTable, routineList);
        }
      }
      break;
    case PRINT:
        { //statement
          data e = eval(expr.op[0], symTable,routineList);
          printData(e);
          res.type = no_op;
          return res;
        }
      break;
    case EQUALS: //statement
        {
          symrec * s = getSymbolFromIdentifier(expr.op[0]->value.id,symTable);
          //check if the variable is function
          routine * r = getRoutine(expr.op[0]->value.id.name, routineList);
          if(s == NULL && r == NULL){
            yyerror("during assignment found unknown variable or function");
            exit(NO_SUCH_VARIABLE);
          }
          //else
          data res;
          if(s!=NULL){
            res = assignment(s,expr.op[1],symTable,routineList);
          }
          if(r!=NULL){
            //TODO check if this is a function or a procedure
            res = r_assignment(r,expr.op[1], symTable,routineList);
          }
          return res;
        }
          break;
    case WHILE: //statement
        { // in ro con ambiente delta valuto <while e to c, omega> --> c <c; while e do c, omega> solo se in ro con ambiente delta posso valutare e a boleano vedi pag 54 semantica opearzionale
          data bool_guard = eval(expr.op[0],symTable,routineList);
          //here typechecking for correct return type of bool_guard...must be boolean
          if(bool_guard.b.b == true){
            eval(expr.op[1],symTable,routineList);
            //ho fatto il comando c, ora rimetto a valutazione la stessa operazione
            treeNode * newWhile = opr(WHILE,2,expr.op[0],expr.op[1]);
            eval(newWhile,symTable,routineList);
            //free(newWhile)
          }
          data res;
          res.type = no_op;
          return res;
        }
        break;
    case IF: //statement
      {
          data bool_guard = eval(expr.op[0],symTable,routineList);
          //here typechecking for correct return type of bool_guard...must be boolean
          if(bool_guard.b.b == true){
            eval(expr.op[1],symTable,routineList);
          }else if(expr.noperands == 3){ //se c'è il branch else
            eval(expr.op[2],symTable,routineList);
          }
          data res;
          res.type = no_op;
          return res;
      }
    break;
    case FOR: //statement
      {
        symrec * s = getSymbolFromIdentifier(expr.op[0]->value.id,symTable);
        if(s == NULL){
          yyerror("NO_SUCH_VARIABLE");
          exit(NO_SUCH_VARIABLE);
        }

        assignment(s,expr.op[1],symTable,routineList);
        identifier index; index.name = malloc(strlen(s->name)+1);
        strcpy(index.name,s->name);
        data id = eval_identifier(index, symTable,routineList);
        //consider only LT
        data guard = eval(expr.op[2],symTable,routineList);
        data comparison = operation(LT, id,guard);
        //here happens typechecking
        if(comparison.b.b == true){
          eval(expr.op[3],symTable,routineList);
          //incremento la variable, assume only integers
          treeNode * nextValue = constantNode(basic_int_value, id.b.i + 1);
          //assignment(s,nextValue,symTable);
          treeNode * newFor = opr(FOR,4,expr.op[0],nextValue,expr.op[2],expr.op[3]);

          eval(newFor,symTable,routineList);
          //free(newFor);
          //free(nextValue);
        }


      }
      break;
    case UMINUS:
    { data e1, e2;
      //typechecking happens here
      e1= eval(expr.op[0],symTable,routineList);
      return negate(e1);
    }
    case MINUS:
    { data e1, e2;
      //typechecking happens here
      e1= eval(expr.op[0],symTable,routineList);
      e2= eval(expr.op[1],symTable,routineList);
      return operation(MINUS, e1,e2);
    }
    break;

    case PLUS :
    { data e1, e2;
      //typechecking happens here
      e1= eval(expr.op[0],symTable,routineList);
      e2= eval(expr.op[1],symTable,routineList);
      return operation(PLUS, e1,e2);
    }
    break;

    case MULTIPLY:
    { data e1, e2;
      //typechecking happens here
      e1= eval(expr.op[0],symTable,routineList);
      e2= eval(expr.op[1],symTable,routineList);
      return operation(MULTIPLY, e1,e2);
    }
    break;

    case DIVIDE :
    { data e1, e2;
      //typechecking happens here
      e1= eval(expr.op[0],symTable,routineList);
      e2= eval(expr.op[1],symTable,routineList);
      return operation(DIVIDE, e1,e2);
    }
    break;
    case LT :
      { data e1, e2;
        //typechecking happens here
        e1= eval(expr.op[0],symTable,routineList);
        e2= eval(expr.op[1],symTable,routineList);
        return operation(LT, e1,e2);
      }
      break;
    case GT :
      { data e1, e2;
        //typechecking happens here
        e1= eval(expr.op[0],symTable,routineList);
        e2= eval(expr.op[1],symTable,routineList);
        return operation(GT, e1,e2);
      }
      break;
    case GE :
      { data e1, e2;
        //typechecking happens here
        e1= eval(expr.op[0],symTable,routineList);
        e2= eval(expr.op[1],symTable,routineList);
        return operation(GE, e1,e2);
      }
      break;
    case LE :
      { data e1, e2;
        //typechecking happens here
        e1= eval(expr.op[0],symTable,routineList);
        e2= eval(expr.op[1],symTable,routineList);
        return operation(LE, e1,e2);
      }
      break;
    case NE :
      { data e1, e2;
        //typechecking happens here
        e1= eval(expr.op[0],symTable,routineList);
        e2= eval(expr.op[1],symTable,routineList);
        return operation(NE, e1,e2);
      }
      break;
    case EQ :
      { data e1, e2;
        //typechecking happens here
        e1= eval(expr.op[0],symTable,routineList);
        e2= eval(expr.op[1],symTable,routineList);
        return operation(EQ, e1,e2);
      }
      break;
    default:
    yyerror("eval_expr new type not implemented");
    exit(NOT_IMPLEMENTED_YET);
    break;
  }
  return res;
}
Exemple #26
0
int
yylex (void)
{
  unichar *start_token;
  unichar ch;

  if (! input_stream_pos)
    {
      fatal ("Input stream not setuped.\n");
      return -1;
    }
  if (mclex_want_line)
    {
      start_token = input_stream_pos;
      if (input_stream_pos[0] == '.'
	  && (input_stream_pos[1] == '\n'
	      || (input_stream_pos[1] == '\r' && input_stream_pos[2] == '\n')))
      {
	mclex_want_line = FALSE;
	while (input_stream_pos[0] != 0 && input_stream_pos[0] != '\n')
	  ++input_stream_pos;
	if (input_stream_pos[0] == '\n')
	  ++input_stream_pos;
	return MCENDLINE;
      }
      while (input_stream_pos[0] != 0 && input_stream_pos[0] != '\n')
	++input_stream_pos;
      if (input_stream_pos[0] == '\n')
	++input_stream_pos;
      yylval.ustr = get_diff (input_stream_pos, start_token);
      return MCLINE;
    }
  while ((ch = input_stream_pos[0]) <= 0x20)
    {
      if (ch == 0)
	return -1;
      ++input_stream_pos;
      if (ch == '\n')
	input_line += 1;
      if (mclex_want_nl && ch == '\n')
	{
	  mclex_want_nl = FALSE;
	  return NL;
	}
    }
  start_token = input_stream_pos;
  ++input_stream_pos;
  if (mclex_want_filename)
    {
      mclex_want_filename = FALSE;
      if (ch == '"')
	{
	  start_token++;
	  while ((ch = input_stream_pos[0]) != 0)
	    {
	      if (ch == '"')
		break;
	      ++input_stream_pos;
	    }
	  yylval.ustr = get_diff (input_stream_pos, start_token);
	  if (ch == '"')
	    ++input_stream_pos;
	}
      else
	{
	  while ((ch = input_stream_pos[0]) != 0)
	    {
	      if (ch <= 0x20 || ch == ')')
		break;
	      ++input_stream_pos;
	    }
	  yylval.ustr = get_diff (input_stream_pos, start_token);
	}
      return MCFILENAME;
    }
  switch (ch)
  {
  case ';':
    ++start_token;
    while (input_stream_pos[0] != '\n' && input_stream_pos[0] != 0)
      ++input_stream_pos;
    if (input_stream_pos[0] == '\n')
      input_stream_pos++;
    yylval.ustr = get_diff (input_stream_pos, start_token);
    return MCCOMMENT;
  case '=':
    return '=';
  case '(':
    return '(';
  case ')':
    return ')';
  case '+':
    return '+';
  case ':':
    return ':';
  case '0': case '1': case '2': case '3': case '4':
  case '5': case '6': case '7': case '8': case '9':
    yylval.ival = parse_digit (ch);
    return MCNUMBER;
  default:
    if (ch >= 0x40)
      {
	int ret;
	while (input_stream_pos[0] >= 0x40 || (input_stream_pos[0] >= '0' && input_stream_pos[0] <= '9'))
	  ++input_stream_pos;
	ret = mc_token (start_token, (size_t) (input_stream_pos - start_token));
	if (ret != -1)
	  return ret;
	yylval.ustr = get_diff (input_stream_pos, start_token);
	return MCIDENT;
      }
    yyerror ("illegal character 0x%x.", ch);
  }
  return -1;
}
int
yyparse (void)
{
    int yystate;
    /* Number of tokens to shift before error messages enabled.  */
    int yyerrstatus;

    /* The stacks and their tools:
       'yyss': related to states.
       'yyvs': related to semantic values.

       Refer to the stacks through separate pointers, to allow yyoverflow
       to reallocate them elsewhere.  */

    /* The state stack.  */
    yytype_int16 yyssa[YYINITDEPTH];
    yytype_int16 *yyss;
    yytype_int16 *yyssp;

    /* The semantic value stack.  */
    YYSTYPE yyvsa[YYINITDEPTH];
    YYSTYPE *yyvs;
    YYSTYPE *yyvsp;

    YYSIZE_T yystacksize;

  int yyn;
  int yyresult;
  /* Lookahead token as an internal (translated) token number.  */
  int yytoken = 0;
  /* The variables used to return semantic value and location from the
     action routines.  */
  YYSTYPE yyval;

#if YYERROR_VERBOSE
  /* Buffer for error messages, and its allocated size.  */
  char yymsgbuf[128];
  char *yymsg = yymsgbuf;
  YYSIZE_T yymsg_alloc = sizeof yymsgbuf;
#endif

#define YYPOPSTACK(N)   (yyvsp -= (N), yyssp -= (N))

  /* The number of symbols on the RHS of the reduced rule.
     Keep to zero when no symbol should be popped.  */
  int yylen = 0;

  yyssp = yyss = yyssa;
  yyvsp = yyvs = yyvsa;
  yystacksize = YYINITDEPTH;

  YYDPRINTF ((stderr, "Starting parse\n"));

  yystate = 0;
  yyerrstatus = 0;
  yynerrs = 0;
  yychar = YYEMPTY; /* Cause a token to be read.  */
  goto yysetstate;

/*------------------------------------------------------------.
| yynewstate -- Push a new state, which is found in yystate.  |
`------------------------------------------------------------*/
 yynewstate:
  /* In all cases, when you get here, the value and location stacks
     have just been pushed.  So pushing a state here evens the stacks.  */
  yyssp++;

 yysetstate:
  *yyssp = yystate;

  if (yyss + yystacksize - 1 <= yyssp)
    {
      /* Get the current used size of the three stacks, in elements.  */
      YYSIZE_T yysize = yyssp - yyss + 1;

#ifdef yyoverflow
      {
        /* Give user a chance to reallocate the stack.  Use copies of
           these so that the &'s don't force the real ones into
           memory.  */
        YYSTYPE *yyvs1 = yyvs;
        yytype_int16 *yyss1 = yyss;

        /* Each stack pointer address is followed by the size of the
           data in use in that stack, in bytes.  This used to be a
           conditional around just the two extra args, but that might
           be undefined if yyoverflow is a macro.  */
        yyoverflow (YY_("memory exhausted"),
                    &yyss1, yysize * sizeof (*yyssp),
                    &yyvs1, yysize * sizeof (*yyvsp),
                    &yystacksize);

        yyss = yyss1;
        yyvs = yyvs1;
      }
#else /* no yyoverflow */
# ifndef YYSTACK_RELOCATE
      goto yyexhaustedlab;
# else
      /* Extend the stack our own way.  */
      if (YYMAXDEPTH <= yystacksize)
        goto yyexhaustedlab;
      yystacksize *= 2;
      if (YYMAXDEPTH < yystacksize)
        yystacksize = YYMAXDEPTH;

      {
        yytype_int16 *yyss1 = yyss;
        union yyalloc *yyptr =
          (union yyalloc *) YYSTACK_ALLOC (YYSTACK_BYTES (yystacksize));
        if (! yyptr)
          goto yyexhaustedlab;
        YYSTACK_RELOCATE (yyss_alloc, yyss);
        YYSTACK_RELOCATE (yyvs_alloc, yyvs);
#  undef YYSTACK_RELOCATE
        if (yyss1 != yyssa)
          YYSTACK_FREE (yyss1);
      }
# endif
#endif /* no yyoverflow */

      yyssp = yyss + yysize - 1;
      yyvsp = yyvs + yysize - 1;

      YYDPRINTF ((stderr, "Stack size increased to %lu\n",
                  (unsigned long int) yystacksize));

      if (yyss + yystacksize - 1 <= yyssp)
        YYABORT;
    }

  YYDPRINTF ((stderr, "Entering state %d\n", yystate));

  if (yystate == YYFINAL)
    YYACCEPT;

  goto yybackup;

/*-----------.
| yybackup.  |
`-----------*/
yybackup:

  /* Do appropriate processing given the current state.  Read a
     lookahead token if we need one and don't already have one.  */

  /* First try to decide what to do without reference to lookahead token.  */
  yyn = yypact[yystate];
  if (yypact_value_is_default (yyn))
    goto yydefault;

  /* Not known => get a lookahead token if don't already have one.  */

  /* YYCHAR is either YYEMPTY or YYEOF or a valid lookahead symbol.  */
  if (yychar == YYEMPTY)
    {
      YYDPRINTF ((stderr, "Reading a token: "));
      yychar = yylex ();
    }

  if (yychar <= YYEOF)
    {
      yychar = yytoken = YYEOF;
      YYDPRINTF ((stderr, "Now at end of input.\n"));
    }
  else
    {
      yytoken = YYTRANSLATE (yychar);
      YY_SYMBOL_PRINT ("Next token is", yytoken, &yylval, &yylloc);
    }

  /* If the proper action on seeing token YYTOKEN is to reduce or to
     detect an error, take that action.  */
  yyn += yytoken;
  if (yyn < 0 || YYLAST < yyn || yycheck[yyn] != yytoken)
    goto yydefault;
  yyn = yytable[yyn];
  if (yyn <= 0)
    {
      if (yytable_value_is_error (yyn))
        goto yyerrlab;
      yyn = -yyn;
      goto yyreduce;
    }

  /* Count tokens shifted since error; after three, turn off error
     status.  */
  if (yyerrstatus)
    yyerrstatus--;

  /* Shift the lookahead token.  */
  YY_SYMBOL_PRINT ("Shifting", yytoken, &yylval, &yylloc);

  /* Discard the shifted token.  */
  yychar = YYEMPTY;

  yystate = yyn;
  YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN
  *++yyvsp = yylval;
  YY_IGNORE_MAYBE_UNINITIALIZED_END

  goto yynewstate;


/*-----------------------------------------------------------.
| yydefault -- do the default action for the current state.  |
`-----------------------------------------------------------*/
yydefault:
  yyn = yydefact[yystate];
  if (yyn == 0)
    goto yyerrlab;
  goto yyreduce;


/*-----------------------------.
| yyreduce -- Do a reduction.  |
`-----------------------------*/
yyreduce:
  /* yyn is the number of a rule to reduce with.  */
  yylen = yyr2[yyn];

  /* If YYLEN is nonzero, implement the default value of the action:
     '$$ = $1'.

     Otherwise, the following line sets YYVAL to garbage.
     This behavior is undocumented and Bison
     users should not rely upon it.  Assigning to YYVAL
     unconditionally makes the parser a bit smaller, and it avoids a
     GCC warning that YYVAL may be used uninitialized.  */
  yyval = yyvsp[1-yylen];


  YY_REDUCE_PRINT (yyn);
  switch (yyn)
    {
        case 2:
#line 49 "parser.y" /* yacc.c:1646  */
    { printf("Valid program. Parsing is Complete.\n");}
#line 1278 "parser.tab.c" /* yacc.c:1646  */
    break;


#line 1282 "parser.tab.c" /* yacc.c:1646  */
      default: break;
    }
  /* User semantic actions sometimes alter yychar, and that requires
     that yytoken be updated with the new translation.  We take the
     approach of translating immediately before every use of yytoken.
     One alternative is translating here after every semantic action,
     but that translation would be missed if the semantic action invokes
     YYABORT, YYACCEPT, or YYERROR immediately after altering yychar or
     if it invokes YYBACKUP.  In the case of YYABORT or YYACCEPT, an
     incorrect destructor might then be invoked immediately.  In the
     case of YYERROR or YYBACKUP, subsequent parser actions might lead
     to an incorrect destructor call or verbose syntax error message
     before the lookahead is translated.  */
  YY_SYMBOL_PRINT ("-> $$ =", yyr1[yyn], &yyval, &yyloc);

  YYPOPSTACK (yylen);
  yylen = 0;
  YY_STACK_PRINT (yyss, yyssp);

  *++yyvsp = yyval;

  /* Now 'shift' the result of the reduction.  Determine what state
     that goes to, based on the state we popped back to and the rule
     number reduced by.  */

  yyn = yyr1[yyn];

  yystate = yypgoto[yyn - YYNTOKENS] + *yyssp;
  if (0 <= yystate && yystate <= YYLAST && yycheck[yystate] == *yyssp)
    yystate = yytable[yystate];
  else
    yystate = yydefgoto[yyn - YYNTOKENS];

  goto yynewstate;


/*--------------------------------------.
| yyerrlab -- here on detecting error.  |
`--------------------------------------*/
yyerrlab:
  /* Make sure we have latest lookahead translation.  See comments at
     user semantic actions for why this is necessary.  */
  yytoken = yychar == YYEMPTY ? YYEMPTY : YYTRANSLATE (yychar);

  /* If not already recovering from an error, report this error.  */
  if (!yyerrstatus)
    {
      ++yynerrs;
#if ! YYERROR_VERBOSE
      yyerror (YY_("syntax error"));
#else
# define YYSYNTAX_ERROR yysyntax_error (&yymsg_alloc, &yymsg, \
                                        yyssp, yytoken)
      {
        char const *yymsgp = YY_("syntax error");
        int yysyntax_error_status;
        yysyntax_error_status = YYSYNTAX_ERROR;
        if (yysyntax_error_status == 0)
          yymsgp = yymsg;
        else if (yysyntax_error_status == 1)
          {
            if (yymsg != yymsgbuf)
              YYSTACK_FREE (yymsg);
            yymsg = (char *) YYSTACK_ALLOC (yymsg_alloc);
            if (!yymsg)
              {
                yymsg = yymsgbuf;
                yymsg_alloc = sizeof yymsgbuf;
                yysyntax_error_status = 2;
              }
            else
              {
                yysyntax_error_status = YYSYNTAX_ERROR;
                yymsgp = yymsg;
              }
          }
        yyerror (yymsgp);
        if (yysyntax_error_status == 2)
          goto yyexhaustedlab;
      }
# undef YYSYNTAX_ERROR
#endif
    }



  if (yyerrstatus == 3)
    {
      /* If just tried and failed to reuse lookahead token after an
         error, discard it.  */

      if (yychar <= YYEOF)
        {
          /* Return failure if at end of input.  */
          if (yychar == YYEOF)
            YYABORT;
        }
      else
        {
          yydestruct ("Error: discarding",
                      yytoken, &yylval);
          yychar = YYEMPTY;
        }
    }

  /* Else will try to reuse lookahead token after shifting the error
     token.  */
  goto yyerrlab1;


/*---------------------------------------------------.
| yyerrorlab -- error raised explicitly by YYERROR.  |
`---------------------------------------------------*/
yyerrorlab:

  /* Pacify compilers like GCC when the user code never invokes
     YYERROR and the label yyerrorlab therefore never appears in user
     code.  */
  if (/*CONSTCOND*/ 0)
     goto yyerrorlab;

  /* Do not reclaim the symbols of the rule whose action triggered
     this YYERROR.  */
  YYPOPSTACK (yylen);
  yylen = 0;
  YY_STACK_PRINT (yyss, yyssp);
  yystate = *yyssp;
  goto yyerrlab1;


/*-------------------------------------------------------------.
| yyerrlab1 -- common code for both syntax error and YYERROR.  |
`-------------------------------------------------------------*/
yyerrlab1:
  yyerrstatus = 3;      /* Each real token shifted decrements this.  */

  for (;;)
    {
      yyn = yypact[yystate];
      if (!yypact_value_is_default (yyn))
        {
          yyn += YYTERROR;
          if (0 <= yyn && yyn <= YYLAST && yycheck[yyn] == YYTERROR)
            {
              yyn = yytable[yyn];
              if (0 < yyn)
                break;
            }
        }

      /* Pop the current state because it cannot handle the error token.  */
      if (yyssp == yyss)
        YYABORT;


      yydestruct ("Error: popping",
                  yystos[yystate], yyvsp);
      YYPOPSTACK (1);
      yystate = *yyssp;
      YY_STACK_PRINT (yyss, yyssp);
    }

  YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN
  *++yyvsp = yylval;
  YY_IGNORE_MAYBE_UNINITIALIZED_END


  /* Shift the error token.  */
  YY_SYMBOL_PRINT ("Shifting", yystos[yyn], yyvsp, yylsp);

  yystate = yyn;
  goto yynewstate;


/*-------------------------------------.
| yyacceptlab -- YYACCEPT comes here.  |
`-------------------------------------*/
yyacceptlab:
  yyresult = 0;
  goto yyreturn;

/*-----------------------------------.
| yyabortlab -- YYABORT comes here.  |
`-----------------------------------*/
yyabortlab:
  yyresult = 1;
  goto yyreturn;

#if !defined yyoverflow || YYERROR_VERBOSE
/*-------------------------------------------------.
| yyexhaustedlab -- memory exhaustion comes here.  |
`-------------------------------------------------*/
yyexhaustedlab:
  yyerror (YY_("memory exhausted"));
  yyresult = 2;
  /* Fall through.  */
#endif

yyreturn:
  if (yychar != YYEMPTY)
    {
      /* Make sure we have latest lookahead translation.  See comments at
         user semantic actions for why this is necessary.  */
      yytoken = YYTRANSLATE (yychar);
      yydestruct ("Cleanup: discarding lookahead",
                  yytoken, &yylval);
    }
  /* Do not reclaim the symbols of the rule whose action triggered
     this YYABORT or YYACCEPT.  */
  YYPOPSTACK (yylen);
  YY_STACK_PRINT (yyss, yyssp);
  while (yyssp != yyss)
    {
      yydestruct ("Cleanup: popping",
                  yystos[*yyssp], yyvsp);
      YYPOPSTACK (1);
    }
#ifndef yyoverflow
  if (yyss != yyssa)
    YYSTACK_FREE (yyss);
#endif
#if YYERROR_VERBOSE
  if (yymsg != yymsgbuf)
    YYSTACK_FREE (yymsg);
#endif
  return yyresult;
}
Exemple #28
0
void
typecheckrange(Node *n)
{
	int op, et;
	Type *t, *t1, *t2;
	Node *v1, *v2;
	NodeList *ll;

	// delicate little dance.  see typecheckas2
	for(ll=n->list; ll; ll=ll->next)
		if(ll->n->defn != n)
			typecheck(&ll->n, Erv | Easgn);

	typecheck(&n->right, Erv);
	if((t = n->right->type) == T)
		goto out;
	n->type = t;

	switch(t->etype) {
	default:
		yyerror("cannot range over %+N", n->right);
		goto out;

	case TARRAY:
		t1 = types[TINT];
		t2 = t->type;
		break;

	case TMAP:
		t1 = t->down;
		t2 = t->type;
		break;

	case TCHAN:
		t1 = t->type;
		t2 = nil;
		if(count(n->list) == 2)
			goto toomany;
		break;

	case TSTRING:
		t1 = types[TINT];
		t2 = types[TINT];
		break;
	}

	if(count(n->list) > 2) {
	toomany:
		yyerror("too many variables in range");
	}

	v1 = n->list->n;
	v2 = N;
	if(n->list->next)
		v2 = n->list->next->n;

	if(v1->defn == n)
		v1->type = t1;
	else if(v1->type != T && checkconv(t1, v1->type, 0, &op, &et) < 0)
		yyerror("cannot assign type %T to %+N", t1, v1);
	if(v2) {
		if(v2->defn == n)
			v2->type = t2;
		else if(v2->type != T && checkconv(t2, v2->type, 0, &op, &et) < 0)
			yyerror("cannot assign type %T to %+N", t1, v1);
	}

out:
	typechecklist(n->nbody, Etop);

	// second half of dance
	n->typecheck = 1;
	for(ll=n->list; ll; ll=ll->next)
		if(ll->n->typecheck == 0)
			typecheck(&ll->n, Erv | Easgn);
}
Exemple #29
0
//
// floating point input
// required syntax is [+-]d*[.]d*[e[+-]d*]
//
void
mpatoflt(Mpflt *a, char *as)
{
	Mpflt b;
	int dp, c, f, ef, ex, eb, zer;
	char *s;

	s = as;
	dp = 0;		/* digits after decimal point */
	f = 0;		/* sign */
	ex = 0;		/* exponent */
	eb = 0;		/* binary point */
	zer = 1;	/* zero */

	mpmovecflt(a, 0.0);
	for(;;) {
		switch(c = *s++) {
		default:
			goto bad;

		case '-':
			f = 1;

		case ' ':
		case  '\t':
		case  '+':
			continue;

		case '.':
			dp = 1;
			continue;

		case '1':
		case '2':
		case '3':
		case '4':
		case '5':
		case '6':
		case '7':
		case '8':
		case '9':
			zer = 0;

		case '0':
			mpmulcflt(a, 10);
			mpaddcflt(a, c-'0');
			if(dp)
				dp++;
			continue;

		case 'P':
		case 'p':
			eb = 1;

		case 'E':
		case 'e':
			ex = 0;
			ef = 0;
			for(;;) {
				c = *s++;
				if(c == '+' || c == ' ' || c == '\t')
					continue;
				if(c == '-') {
					ef = 1;
					continue;
				}
				if(c >= '0' && c <= '9') {
					ex = ex*10 + (c-'0');
					continue;
				}
				break;
			}
			if(ef)
				ex = -ex;

		case 0:
			break;
		}
		break;
	}

	if(eb) {
		if(dp)
			goto bad;
		a->exp += ex;
		goto out;
	}

	if(dp)
		dp--;
	if(mpcmpfltc(a, 0.0) != 0) {
		if(ex >= dp) {
			mppow10flt(&b, ex-dp);
			mpmulfltflt(a, &b);
		} else {
			mppow10flt(&b, dp-ex);
			mpdivfltflt(a, &b);
		}
	}

out:
	if(f)
		mpnegflt(a);
	return;

bad:
	yyerror("set ovf in mpatof");
	mpmovecflt(a, 0.0);
}
Exemple #30
0
static double calluser(struct ufncall *f)
{
  struct symbol *fn = f->s; /* function name */
  struct symlist *sl;       /* dummy arguments */
  struct ast *args = f->l;  /* actual arguments */
  double *oldval, *newval;  /* saved arg values */
  double v;
  int nargs;
  int i;

  if(!fn->func) {
    yyerror("call to undefined function", fn->name);
    return 0;
  }

  /* count the arguments */
  sl = fn->syms;
  for(nargs = 0; sl; sl = sl->next)
    nargs++;

  /* prepare to save them */
  oldval = (double *)malloc(nargs * sizeof(double));
  newval = (double *)malloc(nargs * sizeof(double));
  if(!oldval || !newval) {
    yyerror("Out of space in %s", fn->name); return 0.0;
  }
  
  /* evaluate the arguments */
  for(i = 0; i < nargs; i++) {
    if(!args) {
      yyerror("too few args in call to %s", fn->name);
      free(oldval); free(newval);
      return 0;
    }

    if(args->nodetype == 'L') { /* if this is a list node */
      newval[i] = eval(args->l);
      args = args->r;
    } else {            /* if it's the end of the list */
      newval[i] = eval(args);
      args = NULL;
    }
  }
             
  /* save old values of dummies, assign new ones */
  sl = fn->syms;
  for(i = 0; i < nargs; i++) {
    struct symbol *s = sl->sym;

    oldval[i] = s->value;
    s->value = newval[i];
    sl = sl->next;
  }

  free(newval);

  /* evaluate the function */
  v = eval(fn->func);

  /* put the dummies back */
  sl = fn->syms;
  for(i = 0; i < nargs; i++) {
    struct symbol *s = sl->sym;

    s->value = oldval[i];
    sl = sl->next;
  }

  free(oldval);
  return v;
}