Example #1
0
void Pass1::accept_extern_decl(ParseNode *node)
{
	std::list<ParseNode *>::iterator i = node->children.begin();
	assert((*i)->token == KEYWORD_EXTERN);
	++i;	// i -> prototype-type
	assert((*i)->token == RULE_PROTOTYPE_D_TYPE);
	assert((*i)->children.size() == 1);
	ParseNode *typeident = (*i)->children.front();
	assert(typeident->token == CTokenEnums::TOKEN_IDENT);
	Size size = get_exact_size(typeident->text);
	if(size.scalar == 0)
	{
		throw ParseError(std::string("Externals must have exact size - given: ") + typeident->text,
			node->lineNum, node->fileNum, __LINE__
		);
	}
	++i;	// go to first extern
	for(;;)
	{
		///std::cout << size.exact_size_string() << " - " << (*i)->text << std::endl;
		bool ok = add_extern((*i)->text, size);
		if(!ok)
		{
			throw ParseError("Name already exists - " + (*i)->text,
				node->lineNum,
				node->fileNum,
				__LINE__
			);
		}
	
		++i;
		assert(i != node->children.end());
		if((*i)->token != ',')
			break;
		++i;	// skip comma
	}
}
Example #2
0
/********************************************//**
 * Name:
 *  parse_line
 *
 * Params:
 *  *comp - A pointer to a compiler.
 *
 * Description:
 *  This function will parse the lines.
 *  it will is the standard libraries strtok() function
 *  to break the line in to tokens for further processing.
 *
 * Return:
 *  1 There was a problem parsing the line.
 *  0 The line was parsed successfully.
 *
 ***********************************************/
int parse_line(Compiler *comp) {

	//Create local copy of line so strtok() doesn't destroy the original.
	char *symbol = NULL;
	char *locLine = (char *) malloc(sizeof(char) * MAX_LINE_LEN);
	strcpy(locLine, comp->line);
	char *token = strtok(locLine, " \r\t\n");

	//Check if the line is empty, if it is stop the processing.
	if (token == NULL)
		return 0;

	//Check if the line is a comment, if it is stop the processing.
	if (strstr(token, ";") != NULL)
		return 0;

	//Check if optional label exists, if it does set symbol parameter, and get next token.
	if ((strstr(token, ":")) != NULL) {
		symbol = token;
		CUT_LAST_CHAR(symbol);
		token = strtok(NULL, " \r\t\n");
	}

	//Check if the line is .entry
	if (strstr(comp->line, ".entry") != NULL) {
		token = strtok(NULL, " \r\t\n");
		add_entry(comp, token);
		if (symbol != NULL)
			add_symbol(comp, symbol, DATA);
		return 0;
	}

	//Check if the line is .extern
	if (strstr(comp->line, ".extern") != NULL) {
		token = strtok(NULL, " \r\t\n");
		add_extern(comp, token);
		if (symbol != NULL)
			add_symbol(comp, symbol, DATA);
		return 0;
	}

	//Check if the line is .data
	if (strstr(comp->line, ".data") != NULL) {
		if (symbol != NULL)
			add_symbol(comp, symbol, DATA);
		token = strtok(NULL, " \r\t\n");
		add_data(comp, atoi(token));
		return 0;
	}

	//Check if the line is .string
	if (strstr(comp->line, ".string") != NULL) {
		if (symbol != NULL)
			add_symbol(comp, symbol, DATA);
		token = strtok(NULL, " \r\t\n");
		if (is_valid_string(token))
			add_string(comp, token);
		else
			add_error(comp, comp->fileName, comp->lineIdx, "Missing \"\n");
		return 0;
	}

	//if we got here the the line is code, if it has an optional symbol add it to symbol table.
	if (symbol != NULL)
		add_symbol(comp, symbol, CODE);

	//Add code to the compiler and check if the addition was successful.
	if (!add_code(comp, token, strtok(NULL, " \r\t\n"), strtok(NULL, ","))) {

		//Update the codeLen and dataLen fields
		comp->codeLen = comp->IC;
		comp->dataLen = comp->DC;
		free(locLine);
		return 0;
	}
	add_error(comp, comp->fileName, comp->lineIdx,
			"Incorrect line definition.");
	return 1;
}