Implementing an Options class for EvaluateExpression() in order to make the signature more compact and make it easy to 'just run an expression'

llvm-svn: 163239
This commit is contained in:
Enrico Granata 2012-09-05 20:41:26 +00:00
parent d0855e180d
commit d4439aa9ed
8 changed files with 161 additions and 73 deletions

View File

@ -760,6 +760,105 @@ public:
ClangASTImporter *
GetClangASTImporter();
class EvaluateExpressionOptions
{
public:
EvaluateExpressionOptions() :
m_execution_policy(eExecutionPolicyOnlyWhenNeeded),
m_coerce_to_id(false),
m_unwind_on_error(true),
m_keep_in_memory(false),
m_use_dynamic(lldb::eNoDynamicValues),
m_single_thread_timeout_usec(500000)
{}
ExecutionPolicy
GetExecutionPolicy () const
{
return m_execution_policy;
}
EvaluateExpressionOptions&
SetExecutionPolicy (ExecutionPolicy policy = eExecutionPolicyAlways)
{
m_execution_policy = policy;
return *this;
}
bool
DoesCoerceToId () const
{
return m_coerce_to_id;
}
EvaluateExpressionOptions&
SetCoerceToId (bool coerce = true)
{
m_coerce_to_id = coerce;
return *this;
}
bool
DoesUnwindOnError () const
{
return m_unwind_on_error;
}
EvaluateExpressionOptions&
SetUnwindOnError (bool unwind = false)
{
m_unwind_on_error = unwind;
return *this;
}
bool
DoesKeepInMemory () const
{
return m_keep_in_memory;
}
EvaluateExpressionOptions&
SetKeepInMemory (bool keep = true)
{
m_keep_in_memory = keep;
return *this;
}
lldb::DynamicValueType
GetUseDynamic () const
{
return m_use_dynamic;
}
EvaluateExpressionOptions&
SetUseDynamic (lldb::DynamicValueType dynamic = lldb::eDynamicCanRunTarget)
{
m_use_dynamic = dynamic;
return *this;
}
uint32_t
GetSingleThreadTimeoutUsec () const
{
return m_single_thread_timeout_usec;
}
EvaluateExpressionOptions&
SetSingleThreadTimeoutUsec (uint32_t timeout = 0)
{
m_single_thread_timeout_usec = timeout;
return *this;
}
private:
ExecutionPolicy m_execution_policy;
bool m_coerce_to_id;
bool m_unwind_on_error;
bool m_keep_in_memory;
lldb::DynamicValueType m_use_dynamic;
uint32_t m_single_thread_timeout_usec;
};
// Since expressions results can persist beyond the lifetime of a process,
// and the const expression results are available after a process is gone,
// we provide a way for expressions to be evaluated from the Target itself.
@ -768,13 +867,8 @@ public:
ExecutionResults
EvaluateExpression (const char *expression,
StackFrame *frame,
lldb_private::ExecutionPolicy execution_policy,
bool coerce_to_id,
bool unwind_on_error,
bool keep_in_memory,
lldb::DynamicValueType use_dynamic,
lldb::ValueObjectSP &result_valobj_sp,
uint32_t single_thread_timeout_usec = 500000);
const EvaluateExpressionOptions& options = EvaluateExpressionOptions());
ClangPersistentVariables &
GetPersistentVariables()

View File

@ -1082,17 +1082,14 @@ SBFrame::EvaluateExpression (const char *expr, lldb::DynamicValueType fetch_dyna
Host::SetCrashDescriptionWithFormat ("SBFrame::EvaluateExpression (expr = \"%s\", fetch_dynamic_value = %u) %s",
expr, fetch_dynamic_value, frame_description.GetString().c_str());
#endif
const bool coerce_to_id = false;
const bool keep_in_memory = false;
Target::EvaluateExpressionOptions options;
options.SetUnwindOnError(unwind_on_error)
.SetUseDynamic(fetch_dynamic_value);
exe_results = target->EvaluateExpression (expr,
frame,
eExecutionPolicyOnlyWhenNeeded,
coerce_to_id,
unwind_on_error,
keep_in_memory,
fetch_dynamic_value,
expr_value_sp);
expr_value_sp,
options);
expr_result.SetSP(expr_value_sp);
#ifdef LLDB_CONFIGURATION_DEBUG
Host::SetCrashDescription (NULL);

View File

@ -732,14 +732,12 @@ SBValue::CreateValueFromExpression (const char *name, const char* expression)
Target* target = exe_ctx.GetTargetPtr();
if (target)
{
Target::EvaluateExpressionOptions options;
options.SetKeepInMemory(true);
target->EvaluateExpression (expression,
exe_ctx.GetFramePtr(),
eExecutionPolicyOnlyWhenNeeded,
false, // coerce to id
true, // unwind on error
true, // keep in memory
eNoDynamicValues,
new_value_sp);
new_value_sp,
options);
if (new_value_sp)
{
new_value_sp->SetName(ConstString(name));

View File

@ -298,15 +298,17 @@ CommandObjectExpression::EvaluateExpression
break;
}
Target::EvaluateExpressionOptions options;
options.SetCoerceToId(m_command_options.print_object)
.SetUnwindOnError(m_command_options.unwind_on_error)
.SetKeepInMemory(keep_in_memory)
.SetUseDynamic(use_dynamic)
.SetSingleThreadTimeoutUsec(0);
exe_results = target->EvaluateExpression (expr,
m_interpreter.GetExecutionContext().GetFramePtr(),
eExecutionPolicyOnlyWhenNeeded,
m_command_options.print_object,
m_command_options.unwind_on_error,
keep_in_memory,
use_dynamic,
result_valobj_sp,
0 /* no timeout */);
options);
if (exe_results == eExecutionInterrupted && !m_command_options.unwind_on_error)
{

View File

@ -1201,18 +1201,16 @@ protected:
}
// Use expression evaluation to arrive at the address to watch.
const bool coerce_to_id = true;
const bool unwind_on_error = true;
const bool keep_in_memory = false;
Target::EvaluateExpressionOptions options;
options.SetCoerceToId(false)
.SetUnwindOnError(true)
.SetKeepInMemory(false)
.SetSingleThreadTimeoutUsec(0);
ExecutionResults expr_result = target->EvaluateExpression (expr_str.c_str(),
frame,
eExecutionPolicyOnlyWhenNeeded,
coerce_to_id,
unwind_on_error,
keep_in_memory,
eNoDynamicValues,
valobj_sp,
0 /* no timeout */);
options);
if (expr_result != eExecutionCompleted) {
result.GetErrorStream().Printf("error: expression evaluation of address to watch failed\n");
result.GetErrorStream().Printf("expression evaluated: %s\n", expr_str.c_str());

View File

@ -42,14 +42,17 @@ lldb_private::formatters::CodeRunning_Fetcher (ValueObject &valobj,
StackFrame* stack_frame = exe_ctx.GetFramePtr();
if (!target || !stack_frame)
return false;
Target::EvaluateExpressionOptions options;
options.SetCoerceToId(false)
.SetUnwindOnError(true)
.SetKeepInMemory(true)
.SetUseDynamic(lldb::eDynamicCanRunTarget);
target->EvaluateExpression(expr.GetData(),
stack_frame,
eExecutionPolicyOnlyWhenNeeded,
false,
true,
true,
lldb::eDynamicCanRunTarget,
result_sp);
result_sp,
options);
if (!result_sp)
return false;
value = result_sp->GetValueAsUnsigned(0);
@ -364,14 +367,17 @@ lldb_private::formatters::NSNumber_SummaryProvider (ValueObject& valobj, Stream&
StackFrame* stack_frame = exe_ctx.GetFramePtr();
if (!target || !stack_frame)
return false;
Target::EvaluateExpressionOptions options;
options.SetCoerceToId(false)
.SetUnwindOnError(true)
.SetKeepInMemory(true)
.SetUseDynamic(lldb::eDynamicCanRunTarget);
target->EvaluateExpression(expr.GetData(),
stack_frame,
eExecutionPolicyOnlyWhenNeeded,
false,
true,
true,
lldb::eDynamicCanRunTarget,
result_sp);
result_sp,
options);
if (!result_sp)
return false;
stream.Printf("%s",result_sp->GetSummaryAsCString());

View File

@ -1193,19 +1193,19 @@ CommandInterpreter::PreprocessCommand (std::string &command)
target = Host::GetDummyTarget(GetDebugger()).get();
if (target)
{
const bool coerce_to_id = false;
const bool unwind_on_error = true;
const bool keep_in_memory = false;
ValueObjectSP expr_result_valobj_sp;
Target::EvaluateExpressionOptions options;
options.SetCoerceToId(false)
.SetUnwindOnError(true)
.SetKeepInMemory(false)
.SetSingleThreadTimeoutUsec(0);
ExecutionResults expr_result = target->EvaluateExpression (expr_str.c_str(),
exe_ctx.GetFramePtr(),
eExecutionPolicyOnlyWhenNeeded,
coerce_to_id,
unwind_on_error,
keep_in_memory,
eNoDynamicValues,
exe_ctx.GetFramePtr(),
expr_result_valobj_sp,
0 /* no timeout */);
options);
if (expr_result == eExecutionCompleted)
{
Scalar scalar;

View File

@ -1606,19 +1606,12 @@ Target::EvaluateExpression
(
const char *expr_cstr,
StackFrame *frame,
lldb_private::ExecutionPolicy execution_policy,
bool coerce_to_id,
bool unwind_on_error,
bool keep_in_memory,
lldb::DynamicValueType use_dynamic,
lldb::ValueObjectSP &result_valobj_sp,
uint32_t single_thread_timeout_usec
const EvaluateExpressionOptions& options
)
{
ExecutionResults execution_results = eExecutionSetupError;
result_valobj_sp.reset();
if (expr_cstr == NULL || expr_cstr[0] == '\0')
return execution_results;
@ -1645,7 +1638,7 @@ Target::EvaluateExpression
if (::strcspn (expr_cstr, "()+*&|!~<=/^%,?") == expr_cstr_len)
{
result_valobj_sp = frame->GetValueForVariableExpressionPath (expr_cstr,
use_dynamic,
options.GetUseDynamic(),
expr_path_options,
var_sp,
error);
@ -1679,9 +1672,9 @@ Target::EvaluateExpression
}
else
{
if (use_dynamic != lldb::eNoDynamicValues)
if (options.GetUseDynamic() != lldb::eNoDynamicValues)
{
ValueObjectSP dynamic_sp = result_valobj_sp->GetDynamicValue(use_dynamic);
ValueObjectSP dynamic_sp = result_valobj_sp->GetDynamicValue(options.GetUseDynamic());
if (dynamic_sp)
result_valobj_sp = dynamic_sp;
}
@ -1735,14 +1728,14 @@ Target::EvaluateExpression
const char *prefix = GetExpressionPrefixContentsAsCString();
execution_results = ClangUserExpression::Evaluate (exe_ctx,
execution_policy,
options.GetExecutionPolicy(),
lldb::eLanguageTypeUnknown,
coerce_to_id ? ClangUserExpression::eResultTypeId : ClangUserExpression::eResultTypeAny,
unwind_on_error,
options.DoesCoerceToId() ? ClangUserExpression::eResultTypeId : ClangUserExpression::eResultTypeAny,
options.DoesUnwindOnError(),
expr_cstr,
prefix,
result_valobj_sp,
single_thread_timeout_usec);
options.GetSingleThreadTimeoutUsec());
}
}