Exemplo n.º 1
0
int parser_t::eval_block_node(node_offset_t node_idx, const io_chain_t &io,
                              enum block_type_t block_type) {
    // Paranoia. It's a little frightening that we're given only a node_idx and we interpret this in
    // the topmost execution context's tree. What happens if two trees were to be interleaved?
    // Fortunately that cannot happen (yet); in the future we probably want some sort of reference
    // counted trees.
    parse_execution_context_t *ctx = execution_contexts.back();
    assert(ctx != NULL);

    CHECK_BLOCK(1);

    // Handle cancellation requests. If our block stack is currently empty, then we already did
    // successfully cancel (or there was nothing to cancel); clear the flag. If our block stack is
    // not empty, we are still in the process of cancelling; refuse to evaluate anything.
    if (this->cancellation_requested) {
        if (!block_stack.empty()) {
            return 1;
        }
        this->cancellation_requested = false;
    }

    // Only certain blocks are allowed.
    if ((block_type != TOP) && (block_type != SUBST)) {
        debug(1, INVALID_SCOPE_ERR_MSG, parser_t::get_block_desc(block_type));
        bugreport();
        return 1;
    }

    job_reap(0);  // not sure why we reap jobs here

    /* Start it up */
    const block_t *const start_current_block = current_block();
    block_t *scope_block = new scope_block_t(block_type);
    this->push_block(scope_block);
    int result = ctx->eval_node_at_offset(node_idx, scope_block, io);

    // Clean up the block stack.
    this->pop_block();
    while (start_current_block != current_block()) {
        if (current_block() == NULL) {
            debug(0, _(L"End of block mismatch. Program terminating."));
            bugreport();
            FATAL_EXIT();
            break;
        }
        this->pop_block();
    }

    job_reap(0);  // reap again

    return result;
}
Exemplo n.º 2
0
spv_result_t Function::RegisterSelectionMerge(uint32_t merge_id) {
  RegisterBlock(merge_id, false);
  BasicBlock& merge_block = blocks_.at(merge_id);
  current_block_->set_type(kBlockTypeHeader);
  merge_block.set_type(kBlockTypeMerge);

  AddConstruct({ConstructType::kSelection, current_block(), &merge_block});

  return SPV_SUCCESS;
}
bool LLEasyMessageSender::sendMessage(const LLHost& region_host, const std::string& str_message)
{
	std::vector<std::string> lines = split(str_message, "\n");
	if(!lines.size())
	{
		printError("Not enough information :O");
		return false;
	}
	std::vector<std::string> tokens = split(lines[0], " ");
	if(!tokens.size())
	{
		printError("Not enough information :O");
		return false;
	}
	std::string dir_str = tokens[0];
	LLStringUtil::toLower(dir_str);
	// Direction
	BOOL outgoing;
	if(dir_str == "out")
		outgoing = TRUE;
	else if(dir_str == "in")
		outgoing = FALSE;
	else
	{
		printError("Expected direction 'in' or 'out'");
		return false;
	}
	// Message
	std::string message = "Invalid";
	if(tokens.size() > 1)
	{
		if(tokens.size() > 2)
		{
			printError("Unexpected extra stuff at the top");
			return false;
		}
		message = tokens[1];
		LLStringUtil::trim(message);
	}
	// Body
	std::vector<parts_block> parts;
	if(lines.size() > 1)
	{
		std::vector<std::string>::iterator line_end = lines.end();
		std::vector<std::string>::iterator line_iter = lines.begin();
		++line_iter;
		std::string current_block("");
		int current_block_index = -1;
		for( ; line_iter != line_end; ++line_iter)
		{
			std::string line = (*line_iter);
			LLStringUtil::trim(line);

			//skip empty lines
			if(!line.length())
				continue;

			//check if this line is the start of a new block
			if(line.substr(0, 1) == "[" && line.substr(line.size() - 1, 1) == "]")
			{
				current_block = line.substr(1, line.length() - 2);
				LLStringUtil::trim(current_block);
				++current_block_index;
				parts_block pb;
				pb.name = current_block;
				parts.push_back(pb);
			}
			//should be a key->value pair
			else
			{
				if(current_block.empty())
				{
					printError("Got a field before the start of a block");
					return false;
				}

				int eqpos = line.find("=");
				if(eqpos == line.npos)
				{
					printError("Missing an equal sign");
					return false;
				}

				std::string field = line.substr(0, eqpos);
				LLStringUtil::trim(field);
				if(!field.length())
				{
					printError("Missing name of field");
					return false;
				}

				std::string value = line.substr(eqpos + 1);
				LLStringUtil::trim(value);
				parts_var pv;

				//check if this is a hex value
				if(value.substr(0, 1) == "|")
				{
					pv.hex = TRUE;
					value = value.substr(1);
					LLStringUtil::trim(value);
				}
				else
					pv.hex = FALSE;

				pv.name = field;
				pv.value = value;
				parts[current_block_index].vars.push_back(pv);
			}
		}
	}

	//Make sure everything's kosher with the message we built

	//check if the message type is one that we know about
	std::map<const char *, LLMessageTemplate*>::iterator template_iter;
	template_iter = gMessageSystem->mMessageTemplates.find( LLMessageStringTable::getInstance()->getString(message.c_str()) );
	if(template_iter == gMessageSystem->mMessageTemplates.end())
	{
		printError(llformat("Don't know how to build a '%s' message", message.c_str()));
		return false;
	}

	LLMessageTemplate* temp = (*template_iter).second;

	std::vector<parts_block>::iterator parts_end = parts.end();
	std::vector<parts_block>::iterator parts_iter = parts.begin();
	LLMessageTemplate::message_block_map_t::iterator blocks_end = temp->mMemberBlocks.end();

	for (LLMessageTemplate::message_block_map_t::iterator blocks_iter = temp->mMemberBlocks.begin();
		 blocks_iter != blocks_end; )
	{
		LLMessageBlock* block = (*blocks_iter);
		const char* block_name = block->mName;

		//are we at the end of the block or does this block belongs at this spot in the message?
		if(parts_iter == parts_end || (*parts_iter).name != block_name)
		{
			//did the block end too early?
			if(block->mType != MBT_VARIABLE)
			{
				printError(llformat("Expected '%s' block", block_name));
				return false;
			}

			//skip to the next block
			++blocks_iter;
			continue;
		}

		std::vector<parts_var>::iterator part_var_end = (*parts_iter).vars.end();
		std::vector<parts_var>::iterator part_var_iter = (*parts_iter).vars.begin();
		LLMessageBlock::message_variable_map_t::iterator var_end = block->mMemberVariables.end();
		for (LLMessageBlock::message_variable_map_t::iterator var_iter = block->mMemberVariables.begin();
			 var_iter != var_end; ++var_iter)
		{
			LLMessageVariable* variable = (*var_iter);
			const char* var_name = variable->getName();

			//are there less keypairs in this block than there should be?
			if(part_var_iter == part_var_end || (*part_var_iter).name != var_name)
			{
				printError(llformat("Expected '%s' field under '%s' block", var_name, block_name));
				return false;
			}

			//keep the type of data that this value is supposed to contain for later
			(*part_var_iter).var_type = variable->getType();

			++part_var_iter;
		}

		//there were more keypairs in the block than there should have been
		if(part_var_iter != part_var_end)
		{
			printError(llformat("Unexpected field(s) at end of '%s' block", block_name));
			return false;
		}

		++parts_iter;

		//if this block isn't going to repeat, change to the next block
		if(!((block->mType != MBT_SINGLE) && (parts_iter != parts_end) && ((*parts_iter).name == block_name)))
			++blocks_iter;

	}

	//there were more blocks specified in the message than there should have been
	if(parts_iter != parts_end)
	{
		printError(llformat("Unexpected block(s) at end: %s", (*parts_iter).name.c_str()));
		return false;
	}

	// Build and send
	gMessageSystem->newMessage( message.c_str() );
	for(parts_iter = parts.begin(); parts_iter != parts_end; ++parts_iter)
	{
		const char* block_name = (*parts_iter).name.c_str();
		gMessageSystem->nextBlock(block_name);
		std::vector<parts_var>::iterator part_var_end = (*parts_iter).vars.end();
		for(std::vector<parts_var>::iterator part_var_iter = (*parts_iter).vars.begin();
			part_var_iter != part_var_end; ++part_var_iter)
		{
			parts_var pv = (*part_var_iter);
			if(!addField(pv.var_type, pv.name.c_str(), pv.value, pv.hex))
			{
				printError(llformat("Error adding the provided data for %s '%s' to '%s' block", mvtstr(pv.var_type).c_str(), pv.name.c_str(), block_name));
				gMessageSystem->clearMessage();
				return false;
			}
		}
	}


	if(outgoing)
		return(gMessageSystem->sendMessage(region_host) > 0);
	else
	{
		U8 builtMessageBuffer[MAX_BUFFER_SIZE];

		S32 message_size = gMessageSystem->mTemplateMessageBuilder->buildMessage(builtMessageBuffer, MAX_BUFFER_SIZE, 0);
		gMessageSystem->clearMessage();
		return gMessageSystem->checkMessages(0, true, builtMessageBuffer, region_host, message_size);
	}
}