17 CONFIG_FILE_NETWORK_SECTION,
18 CONFIG_FILE_DEFAULT_SECTION
27 template <
typename Fn>
28 static void MergeSettings(
const Settings &settings,
29 const std::string §ion,
30 const std::string &
name, Fn &&fn) {
44 if (!section.empty()) {
46 if (
auto *values =
FindKey(*map, name)) {
48 Source::CONFIG_FILE_NETWORK_SECTION);
54 if (
auto *values =
FindKey(*map, name)) {
55 fn(
SettingsSpan(*values), Source::CONFIG_FILE_DEFAULT_SECTION);
62 std::map<std::string, SettingsValue> &values,
63 std::vector<std::string> &errors) {
69 if (!file.is_open()) {
75 if (!in.
read(std::string{std::istreambuf_iterator<char>(file),
76 std::istreambuf_iterator<char>()})) {
78 strprintf(
"Unable to parse settings file %s", path.string()));
84 strprintf(
"Failed reading settings file %s", path.string()));
92 strprintf(
"Found non-object value %s in settings file %s",
93 in.
write(), path.string()));
97 const std::vector<std::string> &in_keys = in.
getKeys();
98 const std::vector<SettingsValue> &in_values = in.
getValues();
99 for (
size_t i = 0; i < in_keys.size(); ++i) {
100 auto inserted = values.emplace(in_keys[i], in_values[i]);
101 if (!inserted.second) {
103 strprintf(
"Found duplicate key %s in settings file %s",
104 in_keys[i], path.string()));
107 return errors.empty();
111 const std::map<std::string, SettingsValue> &values,
112 std::vector<std::string> &errors) {
114 for (
const auto &value : values) {
115 out.
__pushKV(value.first, value.second);
121 strprintf(
"Error: Unable to open settings file %s for writing",
125 file << out.
write( 1, 4) << std::endl;
131 const std::string &
name,
132 bool ignore_default_section_config,
133 bool get_chain_name) {
144 const bool never_ignore_negated_setting = span.
last_negated();
151 const bool reverse_precedence =
152 (source == Source::CONFIG_FILE_NETWORK_SECTION ||
153 source == Source::CONFIG_FILE_DEFAULT_SECTION) &&
162 const bool skip_negated_command_line = get_chain_name;
169 if (ignore_default_section_config &&
170 source == Source::CONFIG_FILE_DEFAULT_SECTION &&
171 !never_ignore_negated_setting) {
181 result = reverse_precedence ? span.
begin()[0] : span.
end()[-1];
192 const std::string §ion,
193 const std::string &
name,
194 bool ignore_default_section_config) {
195 std::vector<SettingsValue> result;
198 bool prev_negated_empty =
false;
208 const bool add_zombie_config_values =
209 (source == Source::CONFIG_FILE_NETWORK_SECTION ||
210 source == Source::CONFIG_FILE_DEFAULT_SECTION) &&
214 if (ignore_default_section_config &&
215 source == Source::CONFIG_FILE_DEFAULT_SECTION) {
221 if (!done || add_zombie_config_values) {
222 for (
const auto &value : span) {
223 if (value.isArray()) {
224 result.insert(result.end(), value.getValues().begin(),
225 value.getValues().end());
227 result.push_back(value);
234 done |= span.
negated() > 0 || source == Source::FORCED;
238 prev_negated_empty |= span.
last_negated() && result.empty();
244 const std::string §ion,
245 const std::string &
name) {
246 bool has_default_section_setting =
false;
247 bool has_other_setting =
false;
252 }
else if (source == Source::CONFIG_FILE_DEFAULT_SECTION) {
253 has_default_section_setting =
true;
255 has_other_setting =
true;
261 return has_default_section_setting && !has_other_setting;
267 return data + negated();
273 return size == 0 || last_negated();
276 return size > 0 && data[size - 1].isFalse();
279 for (
size_t i = size; i > 0; --i) {
280 if (data[i - 1].isFalse()) {
std::map< std::string, SettingsValue > rw_settings
Map of setting name to read-write file setting value.
bool OnlyHasDefaultSectionSetting(const Settings &settings, const std::string §ion, const std::string &name)
Return true if a setting is set in the default config file section, and not overridden by a higher pr...
const std::vector< UniValue > & getValues() const
size_t negated() const
Number of negated values.
bool read(const char *raw, size_t len)
SettingsValue GetSetting(const Settings &settings, const std::string §ion, const std::string &name, bool ignore_default_section_config, bool get_chain_name)
Get settings value from combined sources: forced settings, command line arguments, runtime read-write settings, and the read-only config file.
const SettingsValue * end() const
Pointer to end of values.
bool last_negated() const
True if the last value is negated.
const std::vector< std::string > & getKeys() const
auto FindKey(Map &&map, Key &&key) -> decltype(&map.at(key))
Map lookup helper.
std::vector< SettingsValue > GetSettingsList(const Settings &settings, const std::string §ion, const std::string &name, bool ignore_default_section_config)
Get combined setting value similar to GetSetting(), except if setting was specified multiple times...
bool WriteSettings(const fs::path &path, const std::map< std::string, SettingsValue > &values, std::vector< std::string > &errors)
Write settings file.
bool empty() const
True if there are any non-negated values.
std::map< std::string, std::vector< SettingsValue > > command_line_options
Map of setting name to list of command line values.
std::string write(unsigned int prettyIndent=0, unsigned int indentLevel=0) const
const SettingsValue * begin() const
Pointer to first non-negated value.
Accessor for list of settings that skips negated values when iterated over.
std::map< std::string, std::map< std::string, std::vector< SettingsValue > > > ro_config
Map of config section name and setting name to list of config file values.
std::map< std::string, SettingsValue > forced_settings
Map of setting name to forced setting value.
void __pushKV(const std::string &key, const UniValue &val)
bool ReadSettings(const fs::path &path, std::map< std::string, SettingsValue > &values, std::vector< std::string > &errors)
Read settings file.