Exemplo n.º 1
0
  void
Printer::print_sym(Sym *s)
{
  if (s == NULL) {
    fputs("<<null>>", out);
  } else {
    SymTable *st = to<SymTable>(s->get_parent());
    IrObject *par = to<IrObject>(st->get_parent());
    if (is_kind_of<ProcDef>(par)) {
      // We make the local symbol name unique by appending
      // the procedure name as a prefix.
      ProcDef *pd = to<ProcDef>(par);
      fprintf(out, "%s.", get_name(pd).chars());
    } else {
      // We assume that we aren't given nested symbol tables, and
      // thus st must be a global symbol table.  The symbol
      // therefore is global and doesn't need a prefix.
      claim(is_global(st));
#ifndef CFE_NUMERIC_SYMS_FIXED
      // Symbols for literals are coming out of CFE with purely numeric names.
      const char *name = get_name(s).chars();
      if (isdigit(name[0]))
        fprintf(out, "__anon.");
#endif
    }
    fprintf(out, "%s", get_name(s).chars());
  }
}
Exemplo n.º 2
0
void InlineCall::HandleCallNode(Node *&expr){
	if(!expr->isExpression())
		return;
	vector<FuncCallNode*> *container = expr->GetInlineFunction();
	if(!container)
		return;
	Block *block = blocks.top();
	for(int i = 0; i < container->size(); i++){
		FuncCallNode *callNode = container->at(i);
		if(callNode->isRecursiveFuncCallNode())
			continue;
		VarSymbol *var = new VarSymbol("inline_temp" + to_string(inlineCounter), callNode->getType());
		if(!callNode->isVoidFuncCallNode())
			blocks.top()->table->add_symbol(var);
		
		Block *inlineBlock = new Block(*callNode->symbol->body);
		block->body.insert(block->body.begin() + insertIndex + inlineCounter++, dynamic_cast<Node*>(inlineBlock));
		SymTable *formalParams = callNode->symbol->params;
		formalParams->CreateCallParams(/*callNode->args*/);
		HandleBlock(inlineBlock, formalParams, var, inlineBlock->endLabel);
		/*for(int i = 0; i < inlineBlock->body.size(); i++)
			HandleInlineNodeOccur(inlineBlock->body[i], formalParams, var);*/
		if(callNode == expr){
			expr->needDeleteng = true;
			formalParams->InitCallParams(callNode->args, inlineBlock);
		}
		else {
			formalParams->InitCallParams(callNode->args, inlineBlock);
			expr->ReplaceCallNode(callNode, new IdentifierNode(var));
		}
	}
}
Exemplo n.º 3
0
void test_SymbolTableHasName() {
  SymTable global;
  Entity s("hello", "int");
  global.insert(&s);
  assert(global.hasName("hello"));
  assert(!global.hasName("yes"));
}
Exemplo n.º 4
0
SymProc* Parser::ParseProcDecl(string name, vector<string>* argNames, SymTable* argTable, bool isFunc, SymType* Type)
{
	SymTable* locTab = new SymTable;
	TableStack.PushTable(locTab);
	table = TableStack.GetTopTable();
	SymProc* proc = NULL;
	if (isFunc)
	{
		argTable->insert_vo(pair<string, Symbol*>("result", new SymVarParam("result", Type)));
		proc = new	SymFunc(name, argNames, argTable, NULL, false, Type);
	}
	else
		proc = new SymProc(name, argNames, argTable, NULL, false);
	proc->print(os, false);
	if (mainTable->find(name) != mainTable->end())
		mainTable->delete_element(name);
	mainTable->insert(pair<string, SymProc*> (name, proc));
	ParseDecl();
	locTab->MakeLocals();
	proc->SetBody(ParseBlock());
	proc->SetLocTab(locTab);
	TableStack.PopTable();
	TableStack.PopTable();
	table = TableStack.GetTopTable();
	return proc;
}
Exemplo n.º 5
0
void test_ClassSymbolTableInsertion() {
  /* class hello {} */
  SymTable global;
  Entity s("hello", "int");
  global.insert(&s);
  assert(global.find("hello")==&s);
}
Exemplo n.º 6
0
NodeRecordAccess* Parser::ParseRec(NodeExpression* r, SymVar* &name)
{
	SymType* Type = name->GetType();
	if (t.GetValue() == ".")
		while (true)
		{	
			SymTable* tab = ((SymTypeRecord*)(name->GetType()))->GetFields();
			if (t.GetValue() == ".")
				t = sc.GetNextToken();
			_Table::const_iterator _it = tab->find(t.GetValue());
			if (_it == tab->end())
				throw Error("unknown identifier", t);
			name = (SymVar*)(_it->second);
			r = new NodeRecordAccess(new Symbol("."), r, new NodeVar(name));	
			t = sc.GetNextToken();
			if (t.GetValue() == ".")
			{
				Type = name->GetType();
				if (!Type->IsRec())
					throw Error("invalid record access", t);
			}
			else
			{
				Type = name->GetType();
				break;
			}
		}
	r->SetType(Type);
	return (NodeRecordAccess*)r;
}
Exemplo n.º 7
0
NodeCall* Parser::ParseSub(SymProc* sym)
{
	vector<NodeExpression*> params;
	int size = sym->GetArgNames()->size();
	if (size != 0)
	{
		for (int i=0; i<size && t.GetValue() != ")"; ++i)
		{
			t = sc.GetNextToken();
			NodeExpression* p = ParseExpression();
			SymTable* st = sym->GetArgTable();
			SymVarParam* h = (SymVarParam*)(st->find((*(sym->GetArgNames()))[i])->second);
			NodeExpression* help = new NodeExpression(h);
			help->SetType(h->GetType());
			if (p->GetType()->IsScalar() && h->GetType()->IsScalar())
				CheckTypes(help, p, true);
			else
				if (GetRootType(p->GetType()) != GetRootType(help->GetType()))
					throw Error("impossible cast types", t);
			
			params.push_back(p);
		}
		t = RequireToken(")" , "\")\" expected");
	}
	if (params.size() != size)
		throw Error("incorrect number of parameters", t);
	NodeCall* func = new NodeCall(sym, params);
	if (sym->IsFunc())
		func->SetType(sym->GetType());
	return func;
}
Exemplo n.º 8
0
SymTable* Parser::ParseRecDecl(vector<string>* &flds)
{
	vector<string> names;
	Token t1 = sc.GetNextToken();
	t = t1;
	SymTable* fldTable = new SymTable();
	while(t.GetValue() != "end")
	{
		do
		{
			t1 = t;
			t = sc.GetNextToken();
			if (t1.GetType() != identifier && t1.GetValue() != "," && t1.GetValue() != ":")
				throw Error("incorrect record declaration", t);
			if(t1.GetType() == identifier)
			{
				Check(t1.GetValue(), fldTable);
				names.push_back(t1.GetValue());
			}
		}
		while(t.GetValue() != ":");
		SymType* type = ParseType(false);
		for (vector<string>::iterator it = names.begin(); it != names.end(); ++it)
		{
			if (fldTable->find(*it) != fldTable->end())
				throw Error("incorrect record declaration", t);
			fldTable->insert(SymElem (*it, new SymVarLocal(*it, type)));
			flds->push_back((*it));
		}
		names.clear();
		t = sc.GetNextToken();
		t = RequireToken(";" , "\";\" expected");
	}
	return fldTable;
}
Exemplo n.º 9
0
// ** OPI function **
// Install all of the procedure symbols into the external symbol table.
// Skip any NULL entries in halt_proc_syms.
void
install_halt_proc_syms()
{
    SymTable *st = external_sym_table();
    for (int i = halt_proc_syms.size() - 1; i >= 0; --i)
	if (halt_proc_syms[i])
	    st->append_symbol_table_object(halt_proc_syms[i]);
}
Exemplo n.º 10
0
void test_ScopeStackInsert() {
  SymTable t;
  Entity s("a", "class");
  t.insert(&s);
  ScopeStack stack;
  stack.push(&t);
  assert(stack.getEntityByName("a")==&s);
}
Exemplo n.º 11
0
void test_code()
{
  /*
   *
   * class Test {
   *  int a, b;
   *  int fun(int c) {
   *     a = c;
   *     b = 2*c;
   *  }
   * }
   *
   */
  SymTable global;
  Entity cls_test("Test", "class");
  SymTable *classTable = cls_test.getSymTable();
  global.insert(&cls_test);
  Entity a("a", "int");
  Entity b("b", "int");
  Entity meth_fun("fun", "meth");
  Entity c("c", "int");
  classTable->insert(&a);
  classTable->insert(&b);
  classTable->insert(&meth_fun);
  SymTable *methTable = meth_fun.getSymTable();
  methTable->find("params")->getSymTable()->insert(&c);
  assert(true);
  global.printTable();
  //TODO
}
Exemplo n.º 12
0
SymTable* Parser::ParseArguments(vector<string>* &arguments)
{
	SymTable* argTable = new SymTable;
	if (t.GetValue() != "(")
		return argTable;
	vector<string> argNames;
	bool isVar = false;
	do
	{
		t = sc.GetNextToken();
		if (t.GetValue() == "var")
		{
			isVar = true;
			t = sc.GetNextToken();
		}
		if (t.GetType() != identifier)
			throw Error("incorrect name of argument", t);
		argNames.push_back(t.GetValue());
		arguments->push_back(t.GetValue());
		t = sc.GetNextToken();
		if (t.GetValue() == ",")
			continue;
		if (t.GetValue() == ":")
		{
			SymType* Type = ParseType(false);
			if (IsExplType(Type->GetName()))
				throw Error("arguments type mismatch", t);
			t = sc.GetNextToken();
			for(vector<string>::iterator it= argNames.begin(); it != argNames.end(); ++it)
			{
				if (argTable->find(*it) != argTable->end())
					throw Error("identifier already declared",t);
				if (isVar)
					argTable->insert(pair<string, SymVar*> (*it, new SymVarParam_var(*it, Type)));
				else
					argTable->insert(pair<string, SymVar*> (*it, new SymVarParam(*it, Type)));
			}
			isVar = false;
			argNames.clear();
			if (t.GetValue() != ";" && t.GetValue() != ")")
				throw Error("incorrect function defenition", t);
		}
	}
	while(t.GetValue() != ")");
	t = sc.GetNextToken();
	return argTable;
}
Exemplo n.º 13
0
tree
AstIntTypeNode::getSym(
    const char* name,
    SymTable& symTable
    ) const
{
    return symTable.getVar(
        name );
}
Exemplo n.º 14
0
void test_offset()
{
  SymTable global;
  Entity A("A", "class");
  SymTable *A_tab = A.getSymTable();
  global.insert(&A);
  Entity a("a", "int"), b("b", "char"),
    c("c", "int"), d("d", "char");
  Entity meth("func", "meth");
  A_tab->insert(&a);
  A_tab->insert(&b);
  A_tab->insert(&meth);
  SymTable *meth_tab = meth.getSymTable();
  SymTable *p_tab = meth_tab->find("params")->getSymTable();
  p_tab->insert(&c);
  p_tab->insert(&d);
  
}
Exemplo n.º 15
0
bool
AstArrTypeNode::addSym(
    const char* name,
    tree decl,
    SymTable& symTable
    ) const
{
    return symTable.addArr(
        name, -mBegin, decl );
}
Exemplo n.º 16
0
tree
AstArrTypeNode::getSym(
    const char* name,
    SymTable& symTable
    ) const
{
    int off;
    return symTable.getArr(
        name, off );
}
Exemplo n.º 17
0
bool
AstIntTypeNode::addSym(
    const char* name,
    tree decl,
    SymTable& symTable
    ) const
{
    return symTable.addVar(
        name, decl );
}
Exemplo n.º 18
0
void Parser::Init()
{
    SymTable* predefined = new SymTable();
    predefined->Add(intType);
    predefined->Add(floatType);
    predefined->Add(charType);
    symStack.Push(predefined);
    symStack.Push(new SymTable());

    precedences[BOF_] = INF;
    precedences[EOF_] = INF;

    precedences[COMMA] = 1;

    precedences[ASSIGN] = 2;
    precedences[ADD_ASSIGN] = 2;
    precedences[SUB_ASSIGN] = 2;
    precedences[MUL_ASSIGN] = 2;
    precedences[DIV_ASSIGN] = 2;
    precedences[MOD_ASSIGN] = 2;
    precedences[BIT_SHIFT_LEFT_ASSIGN] = 2;
    precedences[BIT_SHIFT_RIGHT_ASSIGN] = 2;
    precedences[BIT_AND_ASSIGN] = 2;
    precedences[BIT_XOR_ASSIGN] = 2;
    precedences[BIT_OR_ASSIGN] = 2;

    precedences[OR] = 3;
    precedences[AND] = 4;

    precedences[BIT_OR] = 5;
    precedences[BIT_XOR] = 6;
    precedences[BIT_AND] = 7;

    precedences[EQUAL] = 8;
    precedences[NOT_EQUAL] = 8;

    precedences[LESS] = 9;
    precedences[GREATER] = 9;
    precedences[LESS_EQUAL] = 9;
    precedences[GREATER_EQUAL] = 9;

    precedences[BIT_SHIFT_LEFT] = 10;
    precedences[BIT_SHIFT_RIGHT] = 10;

    precedences[SUBSTRACTION] = 11;
    precedences[ADDITION] = 11;

    precedences[MULTIPLICATION] = 12;
    precedences[DIVISION] = 12;
    precedences[MODULO] = 12;

    //UNARY operator precedence = 13
    unary_oper[NOT] = true;
    unary_oper[BIT_NOT] = true;
    unary_oper[BIT_AND] = true;// address of an object

    unary_oper[ADDITION] = true;
    unary_oper[SUBSTRACTION] = true;
    unary_oper[MULTIPLICATION] = true;// indirection through a pointer

    precedences[SEMICOLON] = INF;

    //POSTFIX
    precedences[ARROW] = 14;
    precedences[POINT] = 14;

    precedences[ROUND_LEFT_BRACKET] = 14;
    precedences[ROUND_RIGHT_BRACKET] = INF;

    precedences[SQUARE_LEFT_BRACKET] = 14;
    precedences[SQUARE_RIGHT_BRACKET] = INF;

    //Associativity
    right_assoc_oper[NOT] = true;
    right_assoc_oper[BIT_NOT] = true;
    //right_assoc_oper[ADDITION] = true;//unary
    //right_assoc_oper[SUBSTRACTION] = true;//unary
    right_assoc_oper[MULTIPLICATION] = true;

    right_assoc_oper[ASSIGN] = true;
    right_assoc_oper[ADD_ASSIGN] = true;
    right_assoc_oper[SUB_ASSIGN] = true;
    right_assoc_oper[MUL_ASSIGN] = true;
    right_assoc_oper[DIV_ASSIGN] = true;
    right_assoc_oper[MOD_ASSIGN] = true;

    right_assoc_oper[BIT_AND_ASSIGN] = true;
    right_assoc_oper[BIT_XOR_ASSIGN] = true;
    right_assoc_oper[BIT_OR_ASSIGN] = true;
    right_assoc_oper[BIT_SHIFT_LEFT_ASSIGN] = true;
    right_assoc_oper[BIT_SHIFT_RIGHT_ASSIGN] = true;
}
Exemplo n.º 19
0
/*
 * layout_frame -- Assign stack frame locations to each variable that needs one.
 * Store the offsets in frame_map.
 *
 * A local variable needs a memory-stack location unless it is never used or it
 * is a memory-passed parameter.
 */
void
CodeFinIa64::layout_frame()
{
    debug(4, "... determine offsets from $sp for variables");

    // Force max_arg_area to be a 16-byte multiple to be sure that the local-
    // storage area starts on a 16-byte boundary.

    max_arg_area = (max_arg_area + 15) & -16;

    // Unless this is a leaf procedure, reserve a 16-byte scratch area for
    // callees at the young end of the current frame.

    int scratch_area_size = is_leaf ? 0 : 16;

    // Frame_offset is the running offset of the current variable in the
    // local-storage area.  Initialize it to the distance between the young
    // end of the frame and the local-storage area.

    frame_offset = scratch_area_size + max_arg_area;

    SymTable *st = cur_unit->get_symbol_table();
    Iter<SymbolTableObject*> iter = st->get_symbol_table_object_iterator();
    for ( ; iter.is_valid(); iter.next()) {
	SymbolTableObject *sto = iter.current();

	if (is_kind_of<VarSym>(sto)) {
	    VarSym *v = (VarSym*)sto;

	    if (!is_reg_param(v) && is_a<ParameterSymbol>(v))
		continue;				// v's in caller's frame

	    Map<Sym*,int>::iterator v_handle = frame_map.find(v);
	    if (v_handle == frame_map.end())
		continue;				// v never used

	    // Here v is an automatic variable, other than a stack-passed
	    // parameter, that is actually used in the program.  First,
	    // adjust frame_offset to accommodate v'a alignment.  The
	    // frame_offset is already a multiple of four bytes.  An
	    // alignment value greater than four bytes will itself be a
	    // multiple of four.  Round frame_offset up if necessary to
	    // satisfy that alignment constraint.

	    TypeId v_type = get_type(v);
	    int v_align = get_bit_alignment(v_type) >> 3; // in bytes
	    if (v_align > 4) {
		claim(v_align % 4 == 0);
		frame_offset =
		    ((frame_offset + v_align - 1) / v_align) * v_align;
	    }
	    (*v_handle).second = frame_offset;		// update frame_map

	    // Now allocate a multiple of four bytes to v.

	    int v_size = get_bit_size(v_type) >> 3;	// v's size in bytes
	    frame_offset += (v_size + 3) & -4;
	}
    }

    // Compute number of bytes for registers saved in memory between locals
    // and the frame base.
    
    save_area_size = saved_reg_set[CLASS_GR].size() * 8 +
		     saved_reg_set[CLASS_BR].size() * 8 +
		     saved_reg_set[CLASS_FR].size() * 16;

    // The sum of local-area and save-area sizes must be a multiple of 16.
    // Frame_offset is now the local-area size.  Pad it to make the sum a
    // 16-byte multiple.  (Hint: save_area_size is already a multiple of 8.)

    claim((frame_offset & 3) == 0);			// now a 4-byte multiple
    frame_offset = (frame_offset + (save_area_size & 15) + 15) & -16;

    debug(4, "... determine offsets from $sp for memory-passed parameters");

    // Process parameter list in order.  Set running offset param_offset for
    // memory-passed parameters.  Also determine the highest GR arg register
    // used.
    // FIXME: does not allow for aggregates passed partly in regs and partly
    // in memory.

    int param_offset = frame_offset + save_area_size;
    if (param_offset < (scratch_area_size + 16))
	param_offset = (scratch_area_size + 16);

    for (int i = 0; i < get_formal_param_count(cur_unit); i++) {
	VarSym *p = get_formal_param(cur_unit, i);

	// Each parameter consumes a multiple of 8 bytes.

	int p_size = get_bit_size(get_type(p)) >> 3;	// in bytes
	p_size = (p_size + 7) & -8;

	if (is_reg_param(p)) {
	    int first_reg = get_param_reg(p);

	    if (GR_ARG0 <= first_reg && first_reg <= GR_LAST_ARG) {
		claim(first_reg > max_in_reg);

		max_in_reg = first_reg + (p_size / 8) - 1;
		if (max_in_reg > GR_LAST_ARG)
		    max_in_reg = GR_LAST_ARG;
	    }
	} else {
	    claim(frame_map.count(p) == 0);

	    frame_map[p] = param_offset;
	    param_offset += p_size;
	}
    }

    // In a varargs procedure, the GR parameter registers that are not used
    // by named arguments must be spilled to memory adjacent to any
    // parameters passed in memory by the caller.  So in the varargs case,
    // the first thing at the old end of the frame (beginning actually in
    // the caller's scratch area) is a varargs spill area.  Note that we
    // increase max_in_reg to cover any reg-passed, unnamed varargs.

    if (is_varargs) {
	va_area_size = 64 - 8 * (max_in_reg - GR_STACK0 + 1);
	max_in_reg = GR_LAST_ARG;
    } else {
	va_area_size = 0;
    }

    // Frame size is the sum of the sizes of the scratch area, the
    // outgoing-arg area, the local-storage area, the callee-saves-register
    // area, and the register-passed-varargs area.  (The first three have
    // already been combined in frame_offset.)  The sum of frame_offset and
    // save_area_size is already a 16-byte multiple, but va_area_size may
    // not be, so pad to bring frame_size to a multiple of 16 bytes.

    frame_size = frame_offset + save_area_size + ((va_area_size + 15) & -16);

    // For a procedure that invokes va_start, bind the variable whose symbol
    // is stored in va_first_var to the offset from SP of the first unnamed
    // argument, whether passed in memory (va_area_size == 0) or in a register
    // that has been dumped to memory (va_area_size > 0).

    claim((va_first_var == NULL) == (is_varargs == false));
    if (is_varargs)
	frame_map[va_first_var] = 
	    (va_area_size == 0) ? param_offset
				: (frame_size - (va_area_size - 16));
}
Exemplo n.º 20
0
SymProc* Parser::ProcFunc(bool isFunc)
{
	t = sc.GetNextToken();
	SymType* Type = NULL;
	SymProc* sub = NULL;
	if (t.GetType() != identifier)
		throw Error("incorrect procedure name", t);
	SymTable* argTable = NULL;
	vector<string>* argNames = new vector<string>;
	_Table::iterator it = table->find(t.GetValue());
	string name = t.GetValue();
	t = sc.GetNextToken();
	argTable = ParseArguments(argNames);
	TableStack.PushTable(argTable);
	if (isFunc)
	{
		if (t.GetValue() != ":")
			throw Error("type expected", t);
		Type = ParseType(false);
		t = sc.GetNextToken();
	}
	t = RequireToken(";", "\";\" expected");
	if (it != table->end())
	{
		if (!(it->second->IsProc()) || !(((SymProc*)it->second)->IsForward()))
			throw Error("incorrect procedure definition", t);
		SymTable* argTableF = ((SymProc*)it->second)->GetArgTable();
		vector<string>* argNamesF = ((SymProc*)it->second)->GetArgNames();
		for (size_t i=0; i<argNames->size(); ++i)
		{
			if ((*argNames)[i] != (*argNamesF)[i] ||
				!SymComp(argTable->find((*argNames)[i])->second , argTableF->find((*argNamesF)[i])->second))
				throw Error("Header does not match previouse definition", t);
		}
		if (isFunc)
			sub = ParseProcDecl(name, argNames, argTable, true, Type);
		else
			sub = ParseProcDecl(name, argNames, argTable, false, Type);
		t = RequireToken(";", "\";\" expected");
	}
	else
	{
		if (t.GetValue() == "forward")
		{
			t = sc.GetNextToken();
			if (t.GetValue() != ";")
				throw Error("\";\" expected", t);
			if (isFunc)
			{
				sub = new SymFunc(name, argNames, argTable, NULL, true, NULL);
				((SymFunc*)sub)->SetType(Type);
			}
			else
				sub = new SymProc(name, argNames, argTable, NULL, true);
			sub->print(os, false);
			table->insert(pair<string, SymProc*> (name, sub));
			TableStack.PopTable();
		}
		else
		{
			sub = ParseProcDecl(name, argNames, argTable, isFunc, Type);
			if (isFunc)
				((SymFunc*)sub)->SetType(Type);
			sub->GetBody()->print(os, 0);
		}
		t = sc.GetNextToken();
	}
	return sub;
}