aboutsummaryrefslogtreecommitdiff
path: root/lldb/source/Commands/CommandObjectSettings.cpp
diff options
context:
space:
mode:
authorJonas Devlieghere <jonas@devlieghere.com>2018-10-26 00:00:17 +0000
committerJonas Devlieghere <jonas@devlieghere.com>2018-10-26 00:00:17 +0000
commitb76e25a26d37e99ade8c686bf5d6a48d3d20e46d (patch)
treeafbfdea197e064fe50562a021fb62ec3915ade8a /lldb/source/Commands/CommandObjectSettings.cpp
parent24faf859e52b5d06068c3696ca1c89c09ffa2698 (diff)
downloadllvm-b76e25a26d37e99ade8c686bf5d6a48d3d20e46d.zip
llvm-b76e25a26d37e99ade8c686bf5d6a48d3d20e46d.tar.gz
llvm-b76e25a26d37e99ade8c686bf5d6a48d3d20e46d.tar.bz2
Add functionality to export settings
For the reproducer feature I need to be able to export and import the current LLDB configuration. To realize this I've extended the existing functionality to print settings. With the help of a new formatting option, we can now write the settings and their values to a file structured as regular commands. Concretely the functionality works as follows: (lldb) settings export -f /path/to/file This file contains a bunch of settings set commands, followed by the setting's name and value. ... settings set use-external-editor false settings set use-color true settings set auto-one-line-summaries true settings set auto-indent true ... You can import the settings again by either sourcing the file or using the settings read command. (lldb) settings read -f /path/to/file Differential revision: https://reviews.llvm.org/D52651 llvm-svn: 345346
Diffstat (limited to 'lldb/source/Commands/CommandObjectSettings.cpp')
-rw-r--r--lldb/source/Commands/CommandObjectSettings.cpp205
1 files changed, 205 insertions, 0 deletions
diff --git a/lldb/source/Commands/CommandObjectSettings.cpp b/lldb/source/Commands/CommandObjectSettings.cpp
index bde1a80..48ce3753f 100644
--- a/lldb/source/Commands/CommandObjectSettings.cpp
+++ b/lldb/source/Commands/CommandObjectSettings.cpp
@@ -321,6 +321,207 @@ protected:
};
//-------------------------------------------------------------------------
+// CommandObjectSettingsWrite -- Write settings to file
+//-------------------------------------------------------------------------
+
+static constexpr OptionDefinition g_settings_write_options[] = {
+ // clang-format off
+ { LLDB_OPT_SET_ALL, true, "file", 'f', OptionParser::eRequiredArgument, nullptr, {}, CommandCompletions::eDiskFileCompletion, eArgTypeFilename, "The file into which to write the settings." },
+ { LLDB_OPT_SET_ALL, false, "append",'a', OptionParser::eNoArgument, nullptr, {}, 0, eArgTypeNone, "Append to saved settings file if it exists."},
+ // clang-format on
+};
+
+class CommandObjectSettingsWrite : public CommandObjectParsed {
+public:
+ CommandObjectSettingsWrite(CommandInterpreter &interpreter)
+ : CommandObjectParsed(
+ interpreter, "settings export",
+ "Write matching debugger settings and their "
+ "current values to a file that can be read in with "
+ "\"settings read\". Defaults to writing all settings.",
+ nullptr),
+ m_options() {
+ CommandArgumentEntry arg1;
+ CommandArgumentData var_name_arg;
+
+ // Define the first (and only) variant of this arg.
+ var_name_arg.arg_type = eArgTypeSettingVariableName;
+ var_name_arg.arg_repetition = eArgRepeatOptional;
+
+ // There is only one variant this argument could be; put it into the
+ // argument entry.
+ arg1.push_back(var_name_arg);
+
+ // Push the data for the first argument into the m_arguments vector.
+ m_arguments.push_back(arg1);
+ }
+
+ ~CommandObjectSettingsWrite() override = default;
+
+ Options *GetOptions() override { return &m_options; }
+
+ class CommandOptions : public Options {
+ public:
+ CommandOptions() : Options() {}
+
+ ~CommandOptions() override = default;
+
+ Status SetOptionValue(uint32_t option_idx, llvm::StringRef option_arg,
+ ExecutionContext *execution_context) override {
+ Status error;
+ const int short_option = m_getopt_table[option_idx].val;
+
+ switch (short_option) {
+ case 'f':
+ m_filename.assign(option_arg);
+ break;
+ case 'a':
+ m_append = true;
+ break;
+ default:
+ error.SetErrorStringWithFormat("unrecognized option '%c'",
+ short_option);
+ break;
+ }
+
+ return error;
+ }
+
+ void OptionParsingStarting(ExecutionContext *execution_context) override {
+ m_filename.clear();
+ m_append = false;
+ }
+
+ llvm::ArrayRef<OptionDefinition> GetDefinitions() override {
+ return llvm::makeArrayRef(g_settings_write_options);
+ }
+
+ // Instance variables to hold the values for command options.
+ std::string m_filename;
+ bool m_append = false;
+ };
+
+protected:
+ bool DoExecute(Args &args, CommandReturnObject &result) override {
+ std::string path(FileSpec(m_options.m_filename, true).GetPath());
+ uint32_t options = File::OpenOptions::eOpenOptionWrite |
+ File::OpenOptions::eOpenOptionCanCreate;
+ if (m_options.m_append)
+ options |= File::OpenOptions::eOpenOptionAppend;
+ else
+ options |= File::OpenOptions::eOpenOptionTruncate;
+
+ StreamFile out_file(path.c_str(), options,
+ lldb::eFilePermissionsFileDefault);
+
+ if (!out_file.GetFile().IsValid()) {
+ result.AppendErrorWithFormat("%s: unable to write to file", path.c_str());
+ result.SetStatus(eReturnStatusFailed);
+ return false;
+ }
+
+ // Exporting should not be context sensitive.
+ ExecutionContext clean_ctx;
+
+ if (args.empty()) {
+ m_interpreter.GetDebugger().DumpAllPropertyValues(
+ &clean_ctx, out_file, OptionValue::eDumpGroupExport);
+ return result.Succeeded();
+ }
+
+ for (const auto &arg : args) {
+ Status error(m_interpreter.GetDebugger().DumpPropertyValue(
+ &clean_ctx, out_file, arg.ref, OptionValue::eDumpGroupExport));
+ if (!error.Success()) {
+ result.AppendError(error.AsCString());
+ result.SetStatus(eReturnStatusFailed);
+ }
+ }
+
+ return result.Succeeded();
+ }
+
+private:
+ CommandOptions m_options;
+};
+
+//-------------------------------------------------------------------------
+// CommandObjectSettingsRead -- Read settings from file
+//-------------------------------------------------------------------------
+
+static constexpr OptionDefinition g_settings_read_options[] = {
+ // clang-format off
+ {LLDB_OPT_SET_ALL, true, "file",'f', OptionParser::eRequiredArgument, nullptr, {}, CommandCompletions::eDiskFileCompletion, eArgTypeFilename, "The file from which to read the breakpoints." },
+ // clang-format on
+};
+
+class CommandObjectSettingsRead : public CommandObjectParsed {
+public:
+ CommandObjectSettingsRead(CommandInterpreter &interpreter)
+ : CommandObjectParsed(
+ interpreter, "settings read",
+ "Read settings previously saved to a file with \"settings write\".",
+ nullptr),
+ m_options() {}
+
+ ~CommandObjectSettingsRead() override = default;
+
+ Options *GetOptions() override { return &m_options; }
+
+ class CommandOptions : public Options {
+ public:
+ CommandOptions() : Options() {}
+
+ ~CommandOptions() override = default;
+
+ Status SetOptionValue(uint32_t option_idx, llvm::StringRef option_arg,
+ ExecutionContext *execution_context) override {
+ Status error;
+ const int short_option = m_getopt_table[option_idx].val;
+
+ switch (short_option) {
+ case 'f':
+ m_filename.assign(option_arg);
+ break;
+ default:
+ error.SetErrorStringWithFormat("unrecognized option '%c'",
+ short_option);
+ break;
+ }
+
+ return error;
+ }
+
+ void OptionParsingStarting(ExecutionContext *execution_context) override {
+ m_filename.clear();
+ }
+
+ llvm::ArrayRef<OptionDefinition> GetDefinitions() override {
+ return llvm::makeArrayRef(g_settings_read_options);
+ }
+
+ // Instance variables to hold the values for command options.
+ std::string m_filename;
+ };
+
+protected:
+ bool DoExecute(Args &command, CommandReturnObject &result) override {
+ FileSpec file(m_options.m_filename, true);
+ ExecutionContext clean_ctx;
+ CommandInterpreterRunOptions options;
+ options.SetAddToHistory(false);
+ options.SetEchoCommands(false);
+ options.SetPrintResults(true);
+ options.SetStopOnError(false);
+ m_interpreter.HandleCommandsFromFile(file, &clean_ctx, options, result);
+ return result.Succeeded();
+ }
+
+private:
+ CommandOptions m_options;
+};
+
+//-------------------------------------------------------------------------
// CommandObjectSettingsList -- List settable variables
//-------------------------------------------------------------------------
@@ -1007,6 +1208,10 @@ CommandObjectMultiwordSettings::CommandObjectMultiwordSettings(
CommandObjectSP(new CommandObjectSettingsAppend(interpreter)));
LoadSubCommand("clear",
CommandObjectSP(new CommandObjectSettingsClear(interpreter)));
+ LoadSubCommand("write",
+ CommandObjectSP(new CommandObjectSettingsWrite(interpreter)));
+ LoadSubCommand("read",
+ CommandObjectSP(new CommandObjectSettingsRead(interpreter)));
}
CommandObjectMultiwordSettings::~CommandObjectMultiwordSettings() = default;