ultimatepp/uppsrc/ide/Debuggers/VarItem.cpp
cxl ba7ab3ed50 cpp11 branch merged back to to trunk
git-svn-id: svn://ultimatepp.org/upp/trunk@7047 f0d560ea-af0d-0410-9eb7-867de7ffcac7
2014-03-16 16:33:48 +00:00

238 lines
4.8 KiB
C++

#include "VarItem.h"
#include "TypeSimplify.h"
// constructor
VarItem::VarItem(Gdb_MI2 *deb)
{
debugger = deb;
Clear();
}
VarItem::VarItem(Gdb_MI2 *deb, String const &expr)
{
debugger = deb;
Evaluate(expr);
}
// copy
VarItem::VarItem(const VarItem &v)
{
debugger = v.debugger;
empty = v.empty;
simplifyStep = v.simplifyStep;
varName = v.varName;
shortExpression = v.shortExpression;
evaluableExpression = v.evaluableExpression;
type = v.type;
kind = v.kind;
value = v.value;
numChildren = v.numChildren;
items = v.items;
}
// destructor
VarItem::~VarItem()
{
Clear();
}
VarItem const &VarItem::operator=(const VarItem &v)
{
debugger = v.debugger;
empty = v.empty;
simplifyStep = v.simplifyStep;
varName = v.varName;
shortExpression = v.shortExpression;
evaluableExpression = v.evaluableExpression;
type = v.type;
kind = v.kind;
value = v.value;
numChildren = v.numChildren;
items = v.items;
return *this;
}
// clears contents
void VarItem::Clear(void)
{
empty = true;
simplifyStep = -1;
varName.Clear();
shortExpression.Clear();
evaluableExpression.Clear();
type.Clear();
value.Clear();
numChildren = 0;
items = 0;
kind = SIMPLE;
}
bool VarItem::Simplify(void)
{
// if already simplified, return false
if(!simplifyStep)
return false;
// lookup for simplifier
TYPE_SIMPLIFIER_HANDLER simplifier = GetSimplifier(type);
if(!simplifier)
{
// none found, mark as already simplifie and leave
simplifyStep = 0;
return false;
}
// simplifier found
if(simplifyStep == -1)
{
// fast, non-deep simplification
// set simplified to false if need deep one
simplifyStep = simplifier(*this, 0);
}
else
{
// slow, deep simplification
simplifyStep = simplifier(*this, simplifyStep);
}
return (simplifyStep != 0);
}
// evaluate an expression usign gdb variables
bool VarItem::Evaluate(String const &expr)
{
Clear();
// create the variable
MIValue var = debugger->MICmd("var-create - * " + expr);
if(var.IsError())
return false;
empty = false;
// store its name
varName = var["name"];
// store variable name for later cleanup
debugger->StoreVariable(varName);
// store its value
value = var["value"];
// store type
type = var["type"];
// store number of children (temporary number...)
// and set temporary object kind
numChildren = atoi(var.Get("numchild", "0"));
kind = numChildren ? COMPLEX : SIMPLE;
// get and store expression
evaluableExpression = expr;
shortExpression = expr;
// fast simplify known types
Simplify();
return true;
}
// fetch variable children
Vector<VarItem> VarItem::GetChildren0(MIValue const &val, String const &prePath)
{
Vector<VarItem> res;
MIValue const &children = val["children"];
if(!children.IsArray())
return res;
for(int iChild = 0; iChild < children.GetCount(); iChild++)
{
MIValue const &child = children[iChild];
// for private, protected, public and inherited fake childs, just go deeper
String exp = child["exp"];
String typ = child.Get("type", "");
String nam = child.Get("name");
if(exp == "private" || exp == "protected" || exp == "public" || exp == typ)
{
MIValue val2 = debugger->MICmd("var-list-children 1 " + nam);
if(!val2.IsTuple())
continue;
res.Append(GetChildren0(val2, prePath));
}
else
{
VarItem &v = res.Add(VarItem(debugger));
v.empty = false;
v.varName = nam;
v.shortExpression = prePath + "." + exp;
v.type = typ;
v.value = child["value"];
v.numChildren = atoi(child.Get("numchild", "0"));
v.kind = v.numChildren ? COMPLEX : SIMPLE;
MIValue vExp = debugger->MICmd("var-info-path-expression " + nam);
v.evaluableExpression = vExp.Get("path_expr", "");
// fast simplify known types
Simplify();
}
}
return res;
}
// fetch variable children
Vector<VarItem> VarItem::GetChildren(void)
{
Vector<VarItem> res;
// do not enumerate children for non-complex types
// (for arrays and maps just use GetArray and GetMap functions)
if(kind != COMPLEX)
return res;
// if no variable name, just return empty array
if(varName.IsEmpty())
return res;
// get children of current variable
MIValue val = debugger->MICmd("var-list-children 1 " + varName);
if(!val.IsTuple())
return res;
res = GetChildren0(val, evaluableExpression);
return res;
}
// fetch array elements
Vector<VarItem> VarItem::GetArray(int start, int count)
{
Vector<VarItem> res;
return res;
}
// fetch map elements
VectorMap<VarItem, VarItem> VarItem::GetMap(int start, int count)
{
VectorMap<VarItem, VarItem> res;
return res;
}
MIValue VarItem::EvaluateExpression(String const &exp) const
{
MIValue val = debugger->MICmd("data-evaluate-expression " + exp);
if(!val.IsTuple())
return MIValue();
const MIValue& v = val["value"];
if(v.IsError() || !v.IsString())
return MIValue();
String s = v.ToString();
return MIValue(s);
}