/*
 * This function checks to see if the current YAML::Node contains only keys
 * that we care about. Unknown keys should cause PLFS to spit out an error
 * rather than being silently ignored.
 * This is a bit nasty as it drills through the entire tree recursively
 * but it will catch any unknowns in one pass
 *
 * Returns true if all keys are valid
 *
 * Returns false if unknown keys are found and sets bad_key to an error
 * message that points out what key is invalid
 */
bool
is_valid_node(const YAML::Node node, string** bad_key) {
    set<string> key_list(Valid_Keys, 
                         Valid_Keys + 
                         (sizeof(Valid_Keys) / sizeof(Valid_Keys[0]))
                        );
    string key;
    string err = "\nBad key or value in plfsrc: ";
    if(node.IsMap()) {
        for(YAML::const_iterator it=node.begin();it!=node.end();it++) {
            if(!it->first.IsNull()) {
                key = it->first.as<string>();
                if(!is_valid_node(node[key],bad_key)) // recurse
                    return false;
                if(key_list.find(key) == key_list.end()) {
                    err.append(key);
                    *bad_key = new string (err);
                    return false; // this is an unknown key
                }
            }
        }
    }
    else if (node.IsSequence()) {
        for(unsigned int i = 0; i < node.size(); i++)
            if(!is_valid_node(node[i],bad_key)) // recurse
                return false;
    }
    else if (node.IsScalar() && node.as<string>().find(" ") != string::npos) {
        err.append(node.as<string>());
        *bad_key = new string (err);
        return false; // no spaces in values allowed
    }
    return true; // all keys are valid
}
Beispiel #2
0
Datei: yaml.hpp Projekt: k0zmo/kl
inline std::string from_yaml(type_t<std::string>, const YAML::Node& value)
{
    if (!value.IsScalar())
        throw deserialize_error{"type must be a scalar but is " +
                                yaml_type_name(value)};
    return value.Scalar();
}
Beispiel #3
0
// Incrementally load YAML
static NEVER_INLINE void operator +=(YAML::Node& left, const YAML::Node& node)
{
	if (node && !node.IsNull())
	{
		if (node.IsMap())
		{
			for (const auto& pair : node)
			{
				if (pair.first.IsScalar())
				{
					auto&& lhs = left[pair.first.Scalar()];
					lhs += pair.second;
				}
				else
				{
					// Exotic case (TODO: probably doesn't work)
					auto&& lhs = left[YAML::Clone(pair.first)];
					lhs += pair.second;
				}
			}
		}
		else if (node.IsScalar() || node.IsSequence())
		{
			// Scalars and sequences are replaced completely, but this may change in future.
			// This logic may be overwritten by custom demands of every specific cfg:: node.
			left = node;
		}
	}
}
Beispiel #4
0
Datei: yaml.hpp Projekt: k0zmo/kl
Enum enum_from_yaml(const YAML::Node& value,
                    std::true_type /*is_enum_reflectable*/)
{
    if (!value.IsScalar())
        throw deserialize_error{"type must be a scalar but is " +
                                yaml_type_name(value)};
    if (auto enum_value = kl::from_string<Enum>(value.Scalar()))
        return enum_value.get();
    throw deserialize_error{"invalid enum value: " + value.Scalar()};
}
Beispiel #5
0
void Config::parseCommand(const YAML::Node& node, iCommandConfig& config)
{
	//std::cerr << "Under active development!" << '\n';
	//return;
	if(node.size() >= 1 && node.IsMap())
		for (YAML::const_iterator iter=node.begin();iter!=node.end();++iter) {
			std::string key = iter->first.as<std::string>();
			YAML::Node value = iter->second;
			Util::lowercase(key);
			//std::cout << key << std::endl;
			if(key == "command")
			{
				if(value.IsScalar())
				{
					LOG(logger, DEBUG, "Proc: %s", value.as<std::string>().c_str());
					config.command = Util::parseCommand(value.as<std::string>());
#if 0
					// TODO: We need to take quotes from the user and send them all as
					// a single argument instead of multiple arguments.
					std::string cnfval = value.as<std::string>();
					char* cmd = new char[cnfval.size() + 1];
					cmd[cnfval.size()] = 0;
					memcpy(cmd, cnfval.c_str(), cnfval.size());
					size_t size = 1;
					for(size_t i=0; i<cnfval.size(); i++)
						if(cmd[i] == ' ')
							size++;
					config.command = new char*[size+1];
					config.command[size] = 0;
					config.command[0] = cmd;
					size_t csize = 0;
					for(size_t i=0; i<cnfval.size(); i++)
					{
						if(cmd[i] == ' ')
						{
							cmd[i] = 0;
							if(csize < size && (i + 1) < cnfval.size())
							{
								config.command[++csize] = cmd+(unsigned int)i+1;
							}
						}
					}
#endif
				}
			}
			else if( key == "enabled" ) {
				config.enabled = value.as<bool>();
			}
		}
	//for(size_t i=0;config.command[i]; i++)
	//{
	//	std::cout << "==" << config.command[i] << '\n';
	//}
}
Beispiel #6
0
void CopyYaml( const YAML::Node& src, YAML::Node& dst )
{
	if( src.IsNull() ) { return; }
	if( src.IsScalar() ) 
	{ 
		dst = src;
		return;
	};
	
	YAML::Node::const_iterator iter;
	for( iter = src.begin(); iter != src.end(); iter++ )
	{
		dst[ iter->first.as<std::string>() ] = iter->second;
	}
}
Beispiel #7
0
Datei: yaml.hpp Projekt: k0zmo/kl
T from_scalar_yaml(const YAML::Node& value)
{
    if (!value.IsScalar())
        throw deserialize_error{"type must be a scalar but is " +
                                yaml_type_name(value)};

    try
    {
        return value.as<T>();
    }
    catch (const YAML::BadConversion& ex)
    {
        throw deserialize_error{ex.what()};
    }
}
Beispiel #8
0
void Server::tick() {
	YAML::Node tr = _tune.table[_block];

	for (int i = 0; i < int(_channels.size()); i++) {

		if (_tick == 0 && i < int(tr.size()) && !tr[i].IsNull()) {
			string pat = tr[i].as<string>();
			if (!_tune.patterns[pat]) throw logic_error("undefined pattern: " + pat);
			YAML::Node row = _tune.patterns[pat][_row];
			if (row.IsScalar()) {
				auto cmds = get_multi_commands(row.as<string>());
				int l = min(cmds.size(), _channels.size() - i + cmds.size());
				for (int j = 0; j < l; j++) _channels[i + j].set_row_commands(cmds[j]);
			}
		}


		// midi
		if (_midi && i == _tune.midi_channel_nr) {
			struct { unsigned char type, val, x, y; } event;
			for (;;) {
				int l = Pm_Read(_midi, (PmEvent*) &event, 1);
				if (!l) break;

				static int last_note = 0;
				string row;
				if (event.type == 128 && event.val == last_note) row = "---";
				else if (event.type == 144) {
					int i = event.val;
					row	= string(1, "ccddeffggaab"[i%12])
						+ string(1, "-#-#--#-#-#-"[i%12])
						+ string(1, '0' + i/12);
					last_note = event.val;
				}
				if (!row.empty()) _channels[i].set_row_commands({ { "note", row } });

			}
		}

		_channels[i].tick(_tune.instruments);
	}
}
Beispiel #9
0
XmlRpc::XmlRpcValue YamlToXml( const YAML::Node& node )
{
	XmlRpc::XmlRpcValue xml;
	
	if( node.IsNull() ) 
	{ 
		return xml; 
	}
	else if( node.IsSequence() )
	{
		std::vector< std::string > contents = node.as< std::vector< std::string > >();
		xml.setSize( contents.size() );
		for( unsigned int i = 0; i < contents.size(); i++ )
		{
			xml[i] = contents[i];
		}
	}
	else if( node.IsScalar() )
	{
		xml = node.as< std::string >();
	}
	else if( node.IsMap() )
	{
		YAML::Node::const_iterator iter;
		for( iter = node.begin(); iter != node.end(); iter++ )
		{
			std::string name = iter->first.as<std::string>();
			xml[ name ] = YamlToXml( iter->second );
		}
	}
	else
	{
		std::cerr << "Invalid YAML node type." << std::endl;
	}
	return xml;
}
Beispiel #10
0
void cfg::decode(const YAML::Node& data, cfg::_base& rhs)
{
	switch (rhs.get_type())
	{
	case type::node:
	{
		if (data.IsScalar() || data.IsSequence())
		{
			return; // ???
		}

		for (const auto& pair : data)
		{
			if (!pair.first.IsScalar()) continue;

			// Find the key among existing nodes
			for (const auto& _pair : static_cast<node&>(rhs).get_nodes())
			{
				if (_pair.first == pair.first.Scalar())
				{
					decode(pair.second, *_pair.second);
				}
			}
		}

		break;
	}
	case type::set:
	{
		std::vector<std::string> values;

		if (YAML::convert<decltype(values)>::decode(data, values))
		{
			rhs.from_list(std::move(values));
		}

		break;
	}
	case type::log:
	{
		if (data.IsScalar() || data.IsSequence())
		{
			return; // ???
		}

		std::map<std::string, logs::level> values;

		for (const auto& pair : data)
		{
			if (!pair.first.IsScalar() || !pair.second.IsScalar()) continue;

			u64 value;
			if (cfg::try_to_enum_value(&value, &fmt_class_string<logs::level>::format, pair.second.Scalar()))
			{
				values.emplace(pair.first.Scalar(), static_cast<logs::level>(static_cast<int>(value)));
			}
		}

		static_cast<log_entry&>(rhs).set_map(std::move(values));
		break;
	}
	default:
	{
		std::string value;

		if (YAML::convert<std::string>::decode(data, value))
		{
			rhs.from_string(value);
		}

		break; // ???
	}
	}
}
Beispiel #11
0
void Config::parseWatcher(const YAML::Node& node)
{
	size_t asterisk_count;
	if(node.size() >= 1 && node.IsMap())
		for (YAML::const_iterator iter=node.begin();iter!=node.end();++iter) {
			std::string key = iter->first.as<std::string>();
			YAML::Node value = iter->second;
			Util::lowercase(key);
			if(key == "filter")
			{
				if(!value.IsSequence())
					std::cerr << "ERROR!\n";
				for(YAML::const_iterator filter_iter=value.begin();
						filter_iter!=value.end();
						++filter_iter)
				{
					asterisk_count = 0;
					std::string val = filter_iter->as<std::string>();
					for(size_t i = 0; i < val.length(); i++)
						if(val[i] == '*')
							asterisk_count++;
					LOG(logger, DEBUG, "Filter: %s", val.c_str());
					if(asterisk_count > 1)
						throw std::runtime_error("Could not open file");
					mWatch.filters.push_back(val);
				}
			}
			else if(key == "include")
			{
				if(!value.IsSequence() && !value.IsScalar())
					std::cerr << "ERROR!\n";
				if(value.IsSequence())
				{
					for(YAML::const_iterator filter_iter=value.begin();
							filter_iter!=value.end();
							++filter_iter)
					{
						LOG(logger, DEBUG, "Include: %s", filter_iter->as<std::string>().c_str());
						mWatch.include.push_back(filter_iter->as<std::string>());
					}
				}
				else if(value.IsScalar())
				{
					LOG(logger, DEBUG, "Include: %s", value.as<std::string>().c_str());
					mWatch.include.push_back(value.as<std::string>());
				}
			}
			else if(key == "exclude")
			{
				if(!value.IsSequence() && !value.IsScalar())
					std::cerr << "ERROR!\n";
				if(value.IsSequence())
				{
					for(YAML::const_iterator filter_iter=value.begin();
							filter_iter!=value.end();
							++filter_iter)
					{
						LOG(logger, DEBUG, "Exclude: %s", filter_iter->as<std::string>().c_str());
						mWatch.exclude.push_back(filter_iter->as<std::string>());
					}
				}
				else if(value.IsScalar())
				{
					LOG(logger, DEBUG, "Exclude: %s", value.as<std::string>().c_str());
					mWatch.exclude.push_back(value.as<std::string>());
				}
			}
			else
				LOG(logger, DEBUG, "Value: %s\n", value.as<std::string>().c_str());
		}
}