diff --git a/org.ntlab.reverseDebugger/plugin.xml b/org.ntlab.reverseDebugger/plugin.xml
index f9ab0e4..f915beb 100644
--- a/org.ntlab.reverseDebugger/plugin.xml
+++ b/org.ntlab.reverseDebugger/plugin.xml
@@ -18,7 +18,7 @@
+
+
diff --git a/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/JavaEditorOperator.java b/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/JavaEditorOperator.java
index 2927341..90e695c 100644
--- a/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/JavaEditorOperator.java
+++ b/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/JavaEditorOperator.java
@@ -71,7 +71,7 @@
openInJavaEditor(type, method);
}
- private IType findIType(JDIInstanceMethodCaller meCaller) throws InvalidTypeException,
+ public IType findIType(JDIInstanceMethodCaller meCaller) throws InvalidTypeException,
ClassNotLoadedException, InvocationException, IncompatibleThreadStateException {
StringReference declaringClassName = (StringReference)meCaller.callInstanceMethod("getDeclaringClassName");
String projectPath = getLoaderPath(meCaller, declaringClassName);
@@ -154,7 +154,7 @@
return method;
}
- private IMethod findIMethod(IType type, String methodSignature) {
+ public IMethod findIMethod(IType type, String methodSignature) {
try {
for (IMethod method : type.getMethods()) {
if (checkMethodSignature(type, method, methodSignature)) {
diff --git a/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/ReverseDebuggerPerspective.java b/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/ReverseDebuggerPerspective.java
index 6eb0664..405f846 100644
--- a/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/ReverseDebuggerPerspective.java
+++ b/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/ReverseDebuggerPerspective.java
@@ -21,6 +21,10 @@
// �E���ɃI�u�W�F�N�g�t���[�G�C���A�X�̃r���[��z�u
IFolderLayout bottomRight = layout.createFolder("bottomRight", IPageLayout.RIGHT, 0.5f, editorArea);
- bottomRight.addView(ObjectFlowAliasView.ID);
+ bottomRight.addView(ObjectFlowAliasView.ID);
+
+ // �E��ɕϐ��̃r���[��z�u
+ IFolderLayout topRight2 = layout.createFolder("topRight2", IPageLayout.RIGHT, 0.5f, "topLeft");
+ topRight2.addView(VariableView.ID);
}
}
diff --git a/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/SeedAliasView.java b/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/SeedAliasView.java
index 15ff709..88c879b 100644
--- a/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/SeedAliasView.java
+++ b/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/SeedAliasView.java
@@ -28,7 +28,7 @@
private IAction refreshAction;
private IAction resetAction;
private IAction getObjectFlowAction;
- private JDIInstanceMethodCaller selectSeedAlias;
+ private static JDIInstanceMethodCaller selectSeedAlias;
private static SeedAliases seedAliases = new SeedAliases();
private static JavaEditorOperator javaEditorOperator = new JavaEditorOperator();
public static final String ID = "org.ntlab.reverseDebugger.seedAliasView";
@@ -69,6 +69,7 @@
Object element = sel.getFirstElement();
if (element instanceof JDIInstanceMethodCaller) {
selectSeedAlias = (JDIInstanceMethodCaller)element;
+ VariableView.updateVariablesByAlias(selectSeedAlias);
javaEditorOperator.openSrcFileOfAlias(selectSeedAlias);
}
}
@@ -151,10 +152,12 @@
public static void createSeedAliasesByAlias(JDIInstanceMethodCaller alias) {
seedAliases.createSeedAliasesByAlias(alias);
+ VariableView.updateVariablesByAlias(alias);
}
public static void createSeedAliasesByMethodExecution(JDIInstanceMethodCaller methodExecution) {
seedAliases.createSeedAliasesByMethodExecution(methodExecution);
+ VariableView.updateVariablesByMethodExecution(methodExecution);
}
public static void refresh() {
@@ -162,6 +165,7 @@
seedAliases.initSeedAliases();
javaEditorOperator.openSrcFileOfMethodExecution(seedAliases.getDebuggerStopMethodExecution());
CallStackView.reset();
+ VariableView.updateVariablesByMethodExecution(seedAliases.getDebuggerStopMethodExecution());
}
viewer.refresh();
}
@@ -178,4 +182,8 @@
ObjectFlowAliasView.refresh();
}
}
+
+ public static JDIInstanceMethodCaller getSelectSeedAlias() {
+ return selectSeedAlias;
+ }
}
diff --git a/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/VariableLabelProvider.java b/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/VariableLabelProvider.java
new file mode 100644
index 0000000..02cf95f
--- /dev/null
+++ b/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/VariableLabelProvider.java
@@ -0,0 +1,37 @@
+package org.ntlab.reverseDebugger;
+
+import org.eclipse.jface.viewers.ITableLabelProvider;
+import org.eclipse.jface.viewers.LabelProvider;
+import org.eclipse.jface.viewers.TreeNode;
+import org.eclipse.swt.graphics.Image;
+import org.eclipse.ui.ISharedImages;
+import org.eclipse.ui.PlatformUI;
+
+public class VariableLabelProvider extends LabelProvider implements ITableLabelProvider {
+ @Override
+ public String getColumnText(Object element, int columnIndex) {
+ if (element instanceof TreeNode) {
+ Object value = ((TreeNode)element).getValue();
+ if (value instanceof VariableData) {
+ VariableData variableData = (VariableData)value;
+ switch (columnIndex) {
+ case 0:
+ return variableData.getVariableName();
+ case 1:
+ return variableData.getClassName() + " (" + "id = " + variableData.getId() + ")";
+ }
+ }
+ }
+ return "�e�X�g�p�e�L�X�g" + columnIndex;
+ }
+
+ @Override
+ public Image getColumnImage(Object element, int columnIndex) {
+ return getImage(element);
+ }
+
+ @Override
+ public Image getImage(Object element) {
+ return PlatformUI.getWorkbench().getSharedImages().getImage(ISharedImages.IMG_OBJ_ELEMENT);
+ }
+}
diff --git a/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/VariableView.java b/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/VariableView.java
new file mode 100644
index 0000000..8b35044
--- /dev/null
+++ b/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/VariableView.java
@@ -0,0 +1,120 @@
+package org.ntlab.reverseDebugger;
+
+import org.eclipse.jface.action.IMenuManager;
+import org.eclipse.jface.action.IToolBarManager;
+import org.eclipse.jface.viewers.TreeNodeContentProvider;
+import org.eclipse.jface.viewers.TreeViewer;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Tree;
+import org.eclipse.swt.widgets.TreeColumn;
+import org.eclipse.ui.part.ViewPart;
+import org.ntlab.onlineAccessor.JDIInstanceMethodCaller;
+
+public class VariableView extends ViewPart {
+ private static TreeViewer viewer;
+// private IAction refreshAction;
+// private IAction resetAction;
+ private static JDIInstanceMethodCaller selectedAlias;
+ private static Variables variables = new Variables();
+ public static final String ID = "org.ntlab.reverseDebugger.variableView";
+
+ public VariableView() {
+ // TODO Auto-generated constructor stub
+ System.out.println("VariableView�N���X���������ꂽ��!");
+ }
+
+ @Override
+ public void createPartControl(Composite parent) {
+ // TODO Auto-generated method stub
+ System.out.println("VariableView#createPartControl(Composite)���Ăꂽ��!");
+ viewer = new TreeViewer(parent, SWT.BORDER | SWT.H_SCROLL | SWT.V_SCROLL);
+ Tree tree = viewer.getTree();
+ tree.setHeaderVisible(true);
+ tree.setLinesVisible(true);
+
+ String[] treeColumnTexts = {"Name", "Value"};
+ int[] treeColumnWidth = {100, 200};
+ TreeColumn[] treeColumns = new TreeColumn[treeColumnTexts.length];
+ for (int i = 0; i < treeColumns.length; i++) {
+ treeColumns[i] = new TreeColumn(tree, SWT.NULL);
+ treeColumns[i].setText(treeColumnTexts[i]);
+ treeColumns[i].setWidth(treeColumnWidth[i]);
+ }
+ viewer.setContentProvider(new TreeNodeContentProvider());
+ viewer.setLabelProvider(new VariableLabelProvider());
+ JDIInstanceMethodCaller methodExecution = SeedAliasView.getDebuggerStopMethodExecution();
+ if (methodExecution != null) {
+ variables.getAllObjectDataByMethodExecution(methodExecution);
+ viewer.setInput(variables.getVariablesTreeNodes());
+ }
+ createActions();
+ createToolBar();
+ createMenuBar();
+ }
+
+ @Override
+ public void setFocus() {
+ // TODO Auto-generated method stub
+ viewer.getControl().setFocus();
+ }
+
+ private void createActions() {
+// refreshAction = new Action() {
+// @Override
+// public void run() {
+// refresh();
+// }
+// };
+// refreshAction.setText("refresh");
+// refreshAction.setToolTipText("refresh");
+// refreshAction.setImageDescriptor(PlatformUI.getWorkbench().getSharedImages().getImageDescriptor(ISharedImages.IMG_ELCL_SYNCED));
+//
+// resetAction = new Action() {
+// @Override
+// public void run() {
+// reset();
+// }
+// };
+// resetAction.setText("reset");
+// resetAction.setToolTipText("reset");
+// resetAction.setImageDescriptor(PlatformUI.getWorkbench().getSharedImages().getImageDescriptor(ISharedImages.IMG_ETOOL_HOME_NAV));
+ }
+
+ private void createToolBar() {
+ IToolBarManager mgr = getViewSite().getActionBars().getToolBarManager();
+// mgr.add(refreshAction);
+// mgr.add(resetAction);
+ }
+
+ private void createMenuBar() {
+ IMenuManager mgr = getViewSite().getActionBars().getMenuManager();
+// mgr.add(refreshAction);
+// mgr.add(resetAction);
+ }
+
+// public static void refresh() {
+// selectedAlias = SeedAliasView.getSelectSeedAlias();
+// if (selectedAlias != null) {
+// variables.getAllObjectDataByAlias(selectedAlias);
+// viewer.setInput(variables.getVariablesTreeNodes());
+// }
+// }
+
+// private void reset() {
+// selectedAlias = SeedAliasView.getSelectSeedAlias();
+// if (selectedAlias != null) {
+// updateVariablesByAlias(selectedAlias);
+// }
+// }
+
+ public static void updateVariablesByMethodExecution(JDIInstanceMethodCaller methodExecution) {
+ variables.getAllObjectDataByMethodExecution(methodExecution);
+ viewer.setInput(variables.getVariablesTreeNodes());
+ }
+
+ public static void updateVariablesByAlias(JDIInstanceMethodCaller alias) {
+ variables.getAllObjectDataByAlias(alias);
+ viewer.setInput(variables.getVariablesTreeNodes());
+ }
+}
diff --git a/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/Variables.java b/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/Variables.java
new file mode 100644
index 0000000..b8f14b2
--- /dev/null
+++ b/org.ntlab.reverseDebugger/src/org/ntlab/reverseDebugger/Variables.java
@@ -0,0 +1,321 @@
+package org.ntlab.reverseDebugger;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+import org.eclipse.jdt.core.IMethod;
+import org.eclipse.jdt.core.IType;
+import org.eclipse.jdt.core.JavaModelException;
+import org.eclipse.jface.viewers.TreeNode;
+import org.ntlab.onlineAccessor.JDIInstanceMethodCaller;
+import com.sun.jdi.ClassNotLoadedException;
+import com.sun.jdi.ClassType;
+import com.sun.jdi.Field;
+import com.sun.jdi.IncompatibleThreadStateException;
+import com.sun.jdi.IntegerValue;
+import com.sun.jdi.InvalidTypeException;
+import com.sun.jdi.InvocationException;
+import com.sun.jdi.ObjectReference;
+import com.sun.jdi.ReferenceType;
+import com.sun.jdi.StringReference;
+import com.sun.jdi.ThreadReference;
+import com.sun.jdi.Value;
+import com.sun.jdi.VirtualMachine;
+
+public class Variables {
+ private VariableData rootThisObjData;
+ private List argsData = new ArrayList<>();
+ private List allObjData = new ArrayList<>();
+ private static final String TRACER = "org.ntlab.traceAnalysisPlatform.tracer.trace";
+
+ public TreeNode[] getVariablesTreeNodes() {
+ TreeNode[] roots = new TreeNode[allObjData.size()];
+ if (allObjData.isEmpty()) {
+ return roots;
+ }
+ for (int i = 0; i < allObjData.size(); i++) {
+ VariableData rootVariableData = allObjData.get(i);
+ createVariablesTreeNode(null, roots, i, rootVariableData);
+ }
+ return roots;
+ }
+
+ private void createVariablesTreeNode(TreeNode parentNode, TreeNode[] addingNodes, int index, VariableData addingVariableData) {
+ TreeNode newNode = new TreeNode(addingVariableData);
+ newNode.setParent(parentNode);
+ addingNodes[index] = newNode;
+ TreeNode[] childNodes = new TreeNode[addingVariableData.getChildren().size()];
+ addingNodes[index].setChildren(childNodes);
+ for (int i = 0; i < addingVariableData.getChildren().size(); i++) {
+ VariableData child = addingVariableData.getChildren().get(i);
+ createVariablesTreeNode(newNode, childNodes, i, child);
+ }
+ }
+
+ public List getAllObjectDataByMethodExecution(JDIInstanceMethodCaller methodExecution) {
+ if (methodExecution == null) return new ArrayList<>();
+ try {
+ VirtualMachine vm = methodExecution.getVm();
+ ThreadReference thread = methodExecution.getThread();
+ ObjectReference method = methodExecution.getReceiver();
+
+ JDIInstanceMethodCaller mc = new JDIInstanceMethodCaller(vm, thread, method);
+ ObjectReference statements = (ObjectReference)mc.callInstanceMethod("getStatements");
+ mc.changeReceiver(statements);
+ int lastOrder = ((IntegerValue)mc.callInstanceMethod("size")).value() - 1;
+ mc.changeReceiver(method);
+ ObjectReference tp = (ObjectReference)mc.callInstanceMethod("getTracePoint", vm.mirrorOf(lastOrder));
+// methodExecution.getTracePoint(methodExecution.getStatements().size() - 1);
+
+ getAllObjectData(vm, thread, method, tp);
+ } catch (InvalidTypeException | ClassNotLoadedException
+ | InvocationException | IncompatibleThreadStateException e) {
+ e.printStackTrace();
+ }
+ return allObjData;
+ }
+
+ public List getAllObjectDataByAlias(JDIInstanceMethodCaller alias) {
+ if (alias == null) return new ArrayList<>();
+ try {
+ VirtualMachine vm = alias.getVm();
+ ThreadReference thread = alias.getThread();
+ ObjectReference methodExecution = (ObjectReference)alias.callInstanceMethod("getMethodExecution");
+ ObjectReference tp = (ObjectReference)alias.callInstanceMethod("getOccurrencePoint");
+ getAllObjectData(vm, thread, methodExecution, tp);
+ } catch (InvalidTypeException | ClassNotLoadedException | InvocationException
+ | IncompatibleThreadStateException e) {
+ e.printStackTrace();
+ }
+ return allObjData;
+ }
+
+ private void getAllObjectData(VirtualMachine vm, ThreadReference thread, Value methodExecution, Value tp) {
+ try {
+ resetData();
+
+ // this��ID��Type���擾���ĕ\��
+ getRootThisState(vm, thread, (ObjectReference)methodExecution);
+
+ // this�̎��t�B�[���h��ID��Type��\�� (�Ăяo����ōċA)
+ getFieldsState(vm, thread, rootThisObjData, tp, "");
+
+ // ������ID��Type �y�т��̈��������t�B�[���h��ID��Type��\�� (�Ăяo����ōċA)
+ getArgsState(vm, thread, methodExecution, tp, "");
+
+ allObjData.add(rootThisObjData);
+ for (VariableData argData : argsData) {
+ allObjData.add(argData);
+ }
+ } catch (InvalidTypeException | ClassNotLoadedException
+ | InvocationException | IncompatibleThreadStateException e) {
+ e.printStackTrace();
+ }
+ printAllObjData(); // �m�F�p
+ }
+
+ private void getRootThisState(VirtualMachine vm, ThreadReference thread, ObjectReference methodExecution)
+ throws InvalidTypeException, ClassNotLoadedException, InvocationException, IncompatibleThreadStateException {
+ JDIInstanceMethodCaller mc = new JDIInstanceMethodCaller(vm, thread, methodExecution);
+ String thisObjId = ((StringReference)mc.callInstanceMethod("getThisObjId")).value();
+ String thisClassName = ((StringReference)mc.callInstanceMethod("getThisClassName")).value();
+ rootThisObjData = new VariableData("this", thisClassName, thisObjId);
+ }
+
+ private void getFieldsState(VirtualMachine vm, ThreadReference thread, VariableData thisObjData, Value tp, String indent)
+ throws InvalidTypeException, ClassNotLoadedException, InvocationException, IncompatibleThreadStateException {
+ // �t�B�[���h��ID��Type���擾���ĕ\��
+ List classes = vm.classesByName(thisObjData.getClassName());
+ ClassType type = (ClassType)classes.get(0);
+ JDIInstanceMethodCaller mc = new JDIInstanceMethodCaller(vm, thread, null);
+ ObjectReference trace = (ObjectReference)mc.callStaticMethod(TRACER, "TraceJSON", "getInstance");
+ for (Field field : type.allFields()) {
+ if (field.isStatic()) continue; // static�t�B�[���h�͔�� (��낤�Ƃ��Ă��AID��Type�����Ȃ�)
+ String fieldName = field.declaringType().name() + "." + field.name(); // ���S����N���X��
+
+ // ���̃t�B�[���h�ɂ��Ă̍ŐV�̍X�V�����擾(FieldUpdate)
+ mc.changeReceiver(trace);
+ ObjectReference fieldUpdate = (ObjectReference)mc.callInstanceMethod("getRecentlyFieldUpdate", vm.mirrorOf(thisObjData.getId()), vm.mirrorOf(fieldName), tp);
+ if (fieldUpdate == null) continue;
+
+ // �t�B�[���h��ID��Type���擾(String)
+ mc.changeReceiver(fieldUpdate);
+ String fieldObjId = ((StringReference)mc.callInstanceMethod("getValueObjId")).value();
+ String fieldType = ((StringReference)mc.callInstanceMethod("getValueClassName")).value();
+ VariableData fieldData = new VariableData(fieldName, fieldType, fieldObjId);
+ thisObjData.addChild(fieldData);
+
+ // �擾�����t�B�[���h���I�u�W�F�N�g��z��̏ꍇ�ɁA���̃I�u�W�F�N�g��z���t�B�[���h�ɂ��Ă̏������s��
+ callDeepHierarchyFieldState(vm, thread, fieldData, tp, (indent + " "));
+ }
+ }
+
+ /**
+ * �����œn�����t�B�[���h���Q�ƌ^�̏ꍇ��A�z��̏ꍇ�ɁA
+ * ���̎Q�ƌ^�I�u�W�F�N�g�������Ă���t�B�[���h��A�z��̊e�v�f�̃I�u�W�F�N�g�ɂ��āA
+ * ���ꂼ��ɑΉ��������\�b�h������ɌĂяo�� (���̃��\�b�h�ƑΉ����\�b�h�Ƃ̑��ݍċA)
+ */
+ private void callDeepHierarchyFieldState(VirtualMachine vm, ThreadReference thread, VariableData thisObjData, Value tp, String indent)
+ throws InvalidTypeException, ClassNotLoadedException, InvocationException, IncompatibleThreadStateException {
+ // �t�B�[���h��ID��Type���Ȃ��ꍇ��AType(=ActualType)��"---"�̏ꍇ�͉������Ȃ�
+ if (thisObjData.getId() == null || thisObjData.getId().isEmpty()
+ || thisObjData.getClassName() == null || thisObjData.getClassName().isEmpty()) {
+ return;
+ }
+ final String NULL_ACTUAL_TYPE = "---"; // �t�B�[���h�ɑ��Ė����I��null����ꂽ�ꍇ��ActualType�̎擾������
+ if (thisObjData.getClassName().equals(NULL_ACTUAL_TYPE)) return;
+
+ final String ARRAY_SIGNATURE_HEAD = "["; // �z��̃V�O�l�`���̐擪�́A�z��̎��������� [ ���A�Ȃ�
+ if (thisObjData.getClassName().startsWith(ARRAY_SIGNATURE_HEAD)) {
+ // �t�B�[���h��Type���z��^(�@[ �Ŏn�܂�@)�ꍇ (���̔z���e�v�f�ɂ��Ă���Ȃ�f�[�^�擾�������Ăяo��)
+ getArrayState(vm, thread, thisObjData, tp, indent);
+ } else {
+ String[] primitives = {"byte", "short", "int", "long", "float", "double", "char", "boolean"};
+ if (!Arrays.asList(primitives).contains(thisObjData.getClassName())) {
+ // �t�B�[���h��Type���Q�ƌ^(=�I�u�W�F�N�g)�̏ꍇ (���̃I�u�W�F�N�g�������Ă���t�B�[���h�ɂ��Ă���Ȃ�f�[�^�擾�������Ăяo��)
+ getFieldsState(vm, thread, thisObjData, tp, indent);
+ }
+ }
+ }
+
+ private void getArrayState(VirtualMachine vm, ThreadReference thread, VariableData arrayData, Value tp, String indent)
+ throws InvalidTypeException, ClassNotLoadedException, InvocationException, IncompatibleThreadStateException {
+ JDIInstanceMethodCaller mc = new JDIInstanceMethodCaller(vm, thread, null);
+ ObjectReference trace = (ObjectReference)mc.callStaticMethod(TRACER, "TraceJSON", "getInstance");
+ for (int i = 0;; i++){
+ // ���̔z��v�f�ɂ��Ă̍ŐV�̍X�V�����擾(ArrayUpdate)
+ IntegerValue index = vm.mirrorOf(i);
+ mc.changeReceiver(trace);
+ ObjectReference arrayUpdate = (ObjectReference)mc.callInstanceMethod("getRecentlyArrayUpdate", vm.mirrorOf(arrayData.getId()), index, tp);
+ if (arrayUpdate == null) {
+ // �z��̃T�C�Y���擾�ł��Ȃ����߁A�C���f�b�N�X���T�C�Y���߂̂Ƃ��Ɋm���ɔ���������@�Ƃ��ĉ�����
+ // �������A�z��v�f�̓r���ɖ���`���������ꍇ�ł��A�����Ă��܂��̂����_
+ break;
+ }
+ String arrayIndexName = arrayData.getVariableName() + "[" + index.value() + "]";
+
+ // �z��v�f��ID��Type���擾(String)
+ mc.changeReceiver(arrayUpdate);
+ String valueObjId = ((StringReference)mc.callInstanceMethod("getValueObjectId")).value();
+ String valueType = ((StringReference)mc.callInstanceMethod("getValueClassName")).value();
+ VariableData arrayIndexData = new VariableData(arrayIndexName, valueType, valueObjId);
+ arrayData.addChild(arrayIndexData);
+
+ // �擾�����z��v�f���I�u�W�F�N�g��z��̏ꍇ�ɁA���̃I�u�W�F�N�g��z���t�B�[���h�ɂ��Ă̏������s��
+ callDeepHierarchyFieldState(vm, thread, arrayIndexData, tp, (indent + " "));
+ }
+ }
+
+ private void getArgsState(VirtualMachine vm, ThreadReference thread, Value methodExecution, Value tp, String indent)
+ throws InvalidTypeException, ClassNotLoadedException, InvocationException, IncompatibleThreadStateException {
+ // methodExecution������arguments���擾(ArrayList)���A����arguments�̃T�C�Y���擾(int)
+ JDIInstanceMethodCaller mc = new JDIInstanceMethodCaller(vm, thread, (ObjectReference)methodExecution);
+ ObjectReference args = (ObjectReference)mc.callInstanceMethod("getArguments");
+ final int ARGUMENTS_NUM = ((IntegerValue)mc.changeReceiver(args).callInstanceMethod("size")).value();
+ if (ARGUMENTS_NUM > 0) {
+ JavaEditorOperator javaEditorOperator = new JavaEditorOperator();
+ IType type = javaEditorOperator.findIType(new JDIInstanceMethodCaller(vm, thread, (ObjectReference)methodExecution));
+ mc.changeReceiver((ObjectReference)methodExecution);
+ String methodSignature = ((StringReference)mc.callInstanceMethod("getSignature")).value();
+ IMethod method = javaEditorOperator.findIMethod(type, methodSignature);
+ String[] argNames = getParameterNames(method); // ������IMethod���牼���������擾����
+ for (int i = 0; i < ARGUMENTS_NUM; i++) {
+ String argName = (argNames.length == ARGUMENTS_NUM) ? argNames[i] : "arg" + i; // ���Ȃ��Ƃ������̌����s��v�̂Ƃ��͐����������������Ă��Ȃ�
+ mc.changeReceiver(args);
+ ObjectReference arg = (ObjectReference)mc.callInstanceMethod("get", vm.mirrorOf(i));
+ mc.changeReceiver(arg);
+ String argId = ((StringReference)mc.callInstanceMethod("getId")).value();
+ String argType = ((StringReference)mc.callInstanceMethod("getActualType")).value();
+ VariableData argData = new VariableData(argName, argType, argId);
+ argsData.add(argData);
+ callDeepHierarchyFieldState(vm, thread, argData, tp, (indent + " "));
+ }
+ }
+ }
+
+ private String[] getParameterNames(IMethod method) {
+ String[] argNames = new String[0];
+ if (method != null) {
+ try {
+ argNames = method.getParameterNames();
+ } catch (JavaModelException e) {
+ e.printStackTrace();
+ }
+ }
+ return argNames;
+ }
+
+ public void resetData() {
+ rootThisObjData = null;
+ argsData.clear();
+ allObjData.clear();
+ }
+
+ private void printAllObjData() {
+ System.out.println();
+ System.out.println("this");
+ printObjData(allObjData.get(0), "");
+ System.out.println();
+ System.out.println("args");
+ for (int i = 1; i < allObjData.size(); i++) {
+ printObjData(allObjData.get(i), "");
+ }
+ System.out.println();
+ }
+
+ private void printObjData(VariableData data, String indent) {
+ StringBuilder sb = new StringBuilder();
+ sb.append(data.getVariableName() + ": ");
+ sb.append(data.getClassName());
+ sb.append("(" + "id = " + data.getId() + ")");
+ System.out.println(indent + sb);
+ for (VariableData child : data.getChildren()) {
+ printObjData(child, indent + " ");
+ }
+ }
+}
+
+class VariableData {
+ private String variableName;
+ private String className;
+ private String id;
+ private VariableData parent;
+ private List children = new ArrayList<>();
+
+ VariableData(String variableName, String className, String id) {
+ this.variableName = variableName;
+ this.className = className;
+ this.id = id;
+ }
+
+ String getVariableName() {
+ return variableName;
+ }
+
+ String getClassName() {
+ return className;
+ }
+
+ String getId() {
+ return id;
+ }
+
+ VariableData getParent() {
+ return parent;
+ }
+
+ List getChildren() {
+ return children;
+ }
+
+ void addChild(VariableData child) {
+ children.add(child);
+ child.parent = this;
+ }
+
+ @Override
+ public String toString() {
+ return variableName + ": " + className + "(" + "id = " + id + ")";
+ }
+}
\ No newline at end of file