Debugger: Split into core library and application.
[haiku.git] / src / kits / debugger / value / value_nodes / CompoundValueNode.cpp
blobc5dcc61b49e7ceb352e546be862a98d082c95e6d
1 /*
2 * Copyright 2015, Rene Gollent, rene@gollent.com.
3 * Copyright 2009-2012, Ingo Weinhold, ingo_weinhold@gmx.de.
4 * Distributed under the terms of the MIT License.
5 */
8 #include "CompoundValueNode.h"
10 #include <new>
12 #include "Architecture.h"
13 #include "IntegerValue.h"
14 #include "Tracing.h"
15 #include "Type.h"
16 #include "ValueLoader.h"
17 #include "ValueLocation.h"
18 #include "ValueNodeContainer.h"
21 // #pragma mark - Child
24 class CompoundValueNode::Child : public ValueNodeChild {
25 public:
26 Child(CompoundValueNode* parent, const BString& name)
28 fParent(parent),
29 fName(name)
33 virtual const BString& Name() const
35 return fName;
38 virtual ValueNode* Parent() const
40 return fParent;
43 protected:
44 CompoundValueNode* fParent;
45 BString fName;
49 // #pragma mark - BaseTypeChild
52 class CompoundValueNode::BaseTypeChild : public Child {
53 public:
54 BaseTypeChild(CompoundValueNode* parent, BaseType* baseType)
56 Child(parent, baseType->GetType()->Name()),
57 fBaseType(baseType)
59 fBaseType->AcquireReference();
62 virtual ~BaseTypeChild()
64 fBaseType->ReleaseReference();
67 virtual Type* GetType() const
69 return fBaseType->GetType();
72 virtual status_t ResolveLocation(ValueLoader* valueLoader,
73 ValueLocation*& _location)
75 // The parent's location refers to the location of the complete
76 // object. We want to extract the location of a member.
77 ValueLocation* parentLocation = fParent->Location();
78 if (parentLocation == NULL)
79 return B_BAD_VALUE;
81 ValueLocation* location;
82 status_t error = fParent->fType->ResolveBaseTypeLocation(fBaseType,
83 *parentLocation, location);
84 if (error != B_OK) {
85 TRACE_LOCALS("CompoundValueNode::BaseTypeChild::ResolveLocation(): "
86 "ResolveBaseTypeLocation() failed: %s\n", strerror(error));
87 return error;
90 _location = location;
91 return B_OK;
94 private:
95 BaseType* fBaseType;
99 // #pragma mark - MemberChild
102 class CompoundValueNode::MemberChild : public Child {
103 public:
104 MemberChild(CompoundValueNode* parent, DataMember* member)
106 Child(parent, member->Name()),
107 fMember(member)
109 fMember->AcquireReference();
112 virtual ~MemberChild()
114 fMember->ReleaseReference();
117 virtual Type* GetType() const
119 return fMember->GetType();
122 virtual status_t ResolveLocation(ValueLoader* valueLoader,
123 ValueLocation*& _location)
125 // The parent's location refers to the location of the complete
126 // object. We want to extract the location of a member.
127 ValueLocation* parentLocation = fParent->Location();
128 if (parentLocation == NULL)
129 return B_BAD_VALUE;
131 ValueLocation* location;
132 status_t error = fParent->fType->ResolveDataMemberLocation(fMember,
133 *parentLocation, location);
134 if (error != B_OK) {
135 TRACE_LOCALS("CompoundValueNode::MemberChild::ResolveLocation(): "
136 "ResolveDataMemberLocation() failed: %s\n", strerror(error));
137 return error;
140 _location = location;
141 return B_OK;
144 private:
145 DataMember* fMember;
149 // #pragma mark - CompoundValueNode
152 CompoundValueNode::CompoundValueNode(ValueNodeChild* nodeChild,
153 CompoundType* type)
155 ValueNode(nodeChild),
156 fType(type)
158 fType->AcquireReference();
162 CompoundValueNode::~CompoundValueNode()
164 fType->ReleaseReference();
166 for (int32 i = 0; Child* child = fChildren.ItemAt(i); i++)
167 child->ReleaseReference();
171 Type*
172 CompoundValueNode::GetType() const
174 return fType;
178 status_t
179 CompoundValueNode::ResolvedLocationAndValue(ValueLoader* valueLoader,
180 ValueLocation*& _location, Value*& _value)
182 // get the location
183 ValueLocation* location = NodeChild()->Location();
184 if (location == NULL)
185 return B_BAD_VALUE;
187 location->AcquireReference();
188 _location = location;
189 _value = NULL;
190 return B_OK;
194 status_t
195 CompoundValueNode::CreateChildren(TeamTypeInformation* info)
197 if (!fChildren.IsEmpty())
198 return B_OK;
200 // base types
201 for (int32 i = 0; BaseType* baseType = fType->BaseTypeAt(i); i++) {
202 TRACE_LOCALS(" base %" B_PRId32 "\n", i);
204 BaseTypeChild* child = new(std::nothrow) BaseTypeChild(this, baseType);
205 if (child == NULL || !fChildren.AddItem(child)) {
206 delete child;
207 return B_NO_MEMORY;
210 child->SetContainer(fContainer);
213 // members
214 for (int32 i = 0; DataMember* member = fType->DataMemberAt(i); i++) {
215 TRACE_LOCALS(" member %" B_PRId32 ": \"%s\"\n", i, member->Name());
217 MemberChild* child = new(std::nothrow) MemberChild(this, member);
218 if (child == NULL || !fChildren.AddItem(child)) {
219 delete child;
220 return B_NO_MEMORY;
223 child->SetContainer(fContainer);
226 if (fContainer != NULL)
227 fContainer->NotifyValueNodeChildrenCreated(this);
229 return B_OK;
233 int32
234 CompoundValueNode::CountChildren() const
236 return fChildren.CountItems();
240 ValueNodeChild*
241 CompoundValueNode::ChildAt(int32 index) const
243 return fChildren.ItemAt(index);