1/*
2 * Copyright 2009, Ingo Weinhold, ingo_weinhold@gmx.de.
3 * Distributed under the terms of the MIT License.
4 */
5
6#include "StackFrame.h"
7
8#include <new>
9
10#include "CpuState.h"
11#include "FunctionInstance.h"
12#include "Image.h"
13#include "StackFrameDebugInfo.h"
14#include "StackFrameValueInfos.h"
15#include "StackFrameValues.h"
16#include "Variable.h"
17
18
19// #pragma mark - StackFrame
20
21
22StackFrame::StackFrame(stack_frame_type type, CpuState* cpuState,
23	target_addr_t frameAddress, target_addr_t instructionPointer,
24	StackFrameDebugInfo* debugInfo)
25	:
26	fType(type),
27	fCpuState(cpuState),
28	fPreviousCpuState(NULL),
29	fFrameAddress(frameAddress),
30	fInstructionPointer(instructionPointer),
31	fReturnAddress(0),
32	fDebugInfo(debugInfo),
33	fImage(NULL),
34	fFunction(NULL),
35	fValues(NULL),
36	fValueInfos(NULL)
37{
38	fCpuState->AcquireReference();
39	fDebugInfo->AcquireReference();
40}
41
42
43StackFrame::~StackFrame()
44{
45	for (int32 i = 0; Variable* variable = fParameters.ItemAt(i); i++)
46		variable->ReleaseReference();
47
48	for (int32 i = 0; Variable* variable = fLocalVariables.ItemAt(i); i++)
49		variable->ReleaseReference();
50
51	SetImage(NULL);
52	SetFunction(NULL);
53	SetPreviousCpuState(NULL);
54
55	fDebugInfo->ReleaseReference();
56	fCpuState->ReleaseReference();
57}
58
59
60status_t
61StackFrame::Init()
62{
63	// create values map
64	fValues = new(std::nothrow) StackFrameValues;
65	if (fValues == NULL)
66		return B_NO_MEMORY;
67
68	status_t error = fValues->Init();
69	if (error != B_OK)
70		return error;
71
72	// create value infos map
73	fValueInfos = new(std::nothrow) StackFrameValueInfos;
74	if (fValueInfos == NULL)
75		return B_NO_MEMORY;
76
77	error = fValueInfos->Init();
78	if (error != B_OK)
79		return error;
80
81	return B_OK;
82}
83
84
85void
86StackFrame::SetPreviousCpuState(CpuState* state)
87{
88	if (fPreviousCpuState != NULL)
89		fPreviousCpuState->ReleaseReference();
90
91	fPreviousCpuState = state;
92
93	if (fPreviousCpuState != NULL)
94		fPreviousCpuState->AcquireReference();
95}
96
97void
98StackFrame::SetReturnAddress(target_addr_t address)
99{
100	fReturnAddress = address;
101}
102
103
104void
105StackFrame::SetImage(Image* image)
106{
107	if (fImage != NULL)
108		fImage->ReleaseReference();
109
110	fImage = image;
111
112	if (fImage != NULL)
113		fImage->AcquireReference();
114}
115
116
117void
118StackFrame::SetFunction(FunctionInstance* function)
119{
120	if (fFunction != NULL)
121		fFunction->ReleaseReference();
122
123	fFunction = function;
124
125	if (fFunction != NULL)
126		fFunction->AcquireReference();
127}
128
129
130int32
131StackFrame::CountParameters() const
132{
133	return fParameters.CountItems();
134}
135
136
137Variable*
138StackFrame::ParameterAt(int32 index) const
139{
140	return fParameters.ItemAt(index);
141}
142
143
144bool
145StackFrame::AddParameter(Variable* parameter)
146{
147	if (!fParameters.AddItem(parameter))
148		return false;
149
150	parameter->AcquireReference();
151	return true;
152}
153
154
155int32
156StackFrame::CountLocalVariables() const
157{
158	return fLocalVariables.CountItems();
159}
160
161
162Variable*
163StackFrame::LocalVariableAt(int32 index) const
164{
165	return fLocalVariables.ItemAt(index);
166}
167
168
169bool
170StackFrame::AddLocalVariable(Variable* variable)
171{
172	if (!fLocalVariables.AddItem(variable))
173		return false;
174
175	variable->AcquireReference();
176	return true;
177}
178
179
180void
181StackFrame::AddListener(Listener* listener)
182{
183	fListeners.Add(listener);
184}
185
186
187void
188StackFrame::RemoveListener(Listener* listener)
189{
190	fListeners.Remove(listener);
191}
192
193
194void
195StackFrame::NotifyValueRetrieved(Variable* variable, TypeComponentPath* path)
196{
197	for (ListenerList::Iterator it = fListeners.GetIterator();
198			Listener* listener = it.Next();) {
199		listener->StackFrameValueRetrieved(this, variable, path);
200	}
201}
202
203
204// #pragma mark - StackFrame
205
206
207StackFrame::Listener::~Listener()
208{
209}
210
211
212void
213StackFrame::Listener::StackFrameValueRetrieved(StackFrame* stackFrame,
214	Variable* variable, TypeComponentPath* path)
215{
216}
217