Пример #1
0
t_quad_arg quadruple_call(t_quad_arg  arg1) {
	t_quad_arg rt;
	quadruple[quadruple_top].op = QUAD_CALL;
	quadruple[quadruple_top].arg1 = arg1;
	rt.arg_code = ARG_TEMP_IDX;
	rt.val.int_val = push_temp();
	quadruple[quadruple_top].arg2 = rt;
	quadruple[quadruple_top].result.arg_code = 0;
	quadruple_top++;
	return rt;
}
Пример #2
0
t_quad_arg  quadruple_add(t_quad_arg  arg1, t_quad_arg  arg2) {
	t_quad_arg  rt;
	quadruple[quadruple_top].op = QUAD_ADD;
	quadruple[quadruple_top].arg1 = arg1;
	quadruple[quadruple_top].arg2 = arg2;
	rt.arg_code = ARG_TEMP_IDX;
	rt.val.int_val = push_temp();
	quadruple[quadruple_top].result = rt;
	quadruple_top++;
	return rt;
}
Пример #3
0
void
gencode (tree * n)
{
   // custion : only value that are not used after calling another gencode
   // cuz these values are not re-entrent

   static int param_count = 0; // ok
   struct SymbolTable *st;
   char *t1, *t2, new_tmp[MAX_VAR_NAME];

   if (n == NULL)
      return;
   if (isleaf (n))
   {
      checktype(n);
      if(istemp(name(n)))
	 push_temp(name(n));
      else
	 push(name(n));
      return;
   }

   switch(n->type)
   {
      case t_assign:
	 if(isleaf(n->right)) 
	 {
	    fprintf(out, "%s\t:=\t%s\n", name(n->left), name(n->right));
	    break;
	 }
	
	 gencode(n->right->left);
	 gencode(n->right->right);

	 fprintf(out, "%s\t:=\t%s\t%s\t%s\n", name(n->left), pop(), operation(n->right), pop());
	 break;
	
      case t_op:
	 gencode(n->right);
	 gencode(n->left);

	 if(top()->temp)
	 {
	    t1 = pop();
	    t2 = pop();
	    fprintf(out, "%s\t:=\t%s\t%s\t%s\n", t1, t1, operation(n), t2);	
	    push_temp(t1);
	    break;
	 }
	 t1 = pop();
	 t2 = pop();
	 sprintf(new_tmp, "_t%d", last_temp++);
	 fprintf(out, "%s\t:=\t%s\t%s\t%s\n", new_tmp, t1, operation(n), t2);	
	 push_temp(new_tmp);
	
	 break;

      case t_goto:
	 st = lookup(name(n->left));
	 if(st && (gettype(name(n->left)) == LABEL))
	    fprintf(out, "%s\t%s\n", operation(n), name(n->left));
	 else {
	    add(name(n->left), LABEL);
	    st = lookup(name(n->left));
	    st->ok = 0;		// waitting to see label defination
	    fprintf(stderr, "Warning: waitting to see label(%s)\n", name(n->left));
	 }
	 break;

      case t_while: {
	 int  Lbegin = newlabel();
	 int  Lend = newlabel();
	 fprintf(out, "_l%d\t:\n", Lbegin);
	 
	 if(isleaf(n->left)) {
	    fprintf(out, "if\t%s\t=\t0\tgoto\t_l%d\n", name(n->left), Lend);
	 } else {		/* TODO : it SHLULD be relop but we dont check */
	    gencode(n->left->left);
	    gencode(n->left->right);
	    
	    fprintf(out, "if\t%s\t%s\t%s\tgoto\t_l%d\n", pop(), neg_operation(n->left), pop(), Lend);
	 }
	 gencode(n->right);
	 fprintf(out, "goto\t_l%d\n", Lbegin);
	 fprintf(out, "_l%d\t:\n", Lend);
	 break;
      }

      case t_for: 
	 fprintf(stderr, "No impl for FOR yet!\n");
	 break;

      case t_sub:
	 gencode(n->right);
	 fprintf(out, "call\t%s\t%d\n", n->left->value.idval, param_count);
	 param_count = 0;
	 break;

      case t_param:
	 gencode(n->left);
	 fprintf(out, "param\t%s\n", pop());
	 param_count++;
	 if(n->right) 
	    gencode(n->right);
	 break;

      case t_if:
      {
	 int L = newlabel();
	 if(isleaf(n->left)) {
	   fprintf(out, "if\t%s\t=\t0\tgoto\t_l%d\n", name(n->left), L);
	 } else {		/* TODO : it SHLULD be relop but we dont check */
	   gencode(n->left->left);
	   gencode(n->left->right);
	   
	   fprintf(out, "if\t%s\t%s\t%s\tgoto\t_l%d\n", pop(), operation(n->left), pop(), L);
	 }
	 gencode(n->right->left);

	 // else
	 if(n->right->right != NULL)
	 {
	    int L2 = newlabel();
	    fprintf(out, "goto\t_l%d\n", L2);
	    fprintf(out, "_l%d\t:\n", L);
	    gencode(n->right->right);
	    fprintf(out, "_l%d\t:\n", L2);
	 } else {
	    fprintf(out, "_l%d\t:\n", L);
	 }
	 break;
      }

      case t_join:
	 if(n->op == LABEL_JOIN)
	 {
	    add(n->left->value.idval, LABEL);
	    fprintf(out, "%s\t:\n", n->left->value.idval);
	 }
	 else
	    gencode(n->left);
	 gencode(n->right);
	 break;

      case t_block:
	 gencode(n->left);
	 break;
   }
   // switch
}