Community
Participate
Eclipse IDE
two references point to the same object, initially their values are displayed correctly, according to Variables View. When one reference changes by pressing F6, Variables View refresh the value of this refrence, but does NOT refresh another. example code: /* * Created on 2004-4-16 * @author Skee */ package showbug; public class BugString { class A { private int i = 3; void setI(int j) { i = j; } int getI() { return i; } } public void show() { A a = new A(); A aliasA = a; System.out.println("\tbefore change"); System.out.println("a:" + a.getI() + "\taliasA:" + aliasA.getI()); a.setI(5); System.out.println("\tafter change"); System.out.println("a:" + a.getI() + "\taliasA:" + aliasA.getI()); } public static void main(String[] args) { BugString bs = new BugString(); bs.show(); } }
This is a problem with any duplicate element in a tree view. In this case, i is a JDIField which appears twice in the Variables tree view. When the label is updated, StructuredViewer.update is driven with the value change of i. The StructuredViewer assumes that all elements are unique and will only locate the first occurence of the element.
Thanks for the analysis (I suspected something like that)
Michael, did you have any ideas on a possible fix hear?
The TreeViewer isn't conducive to duplicate elements. The only solution I have is very messy. All elements added to the LabelJob are wrappered with a count. When duplicate elements are detected, the count is increased. DebugViewDecoratingLabelProvider.labelsComputed can have the elements updated and then do each element that is > 1 as many times as necessary. A comparer needs to be added to handle these special elements. When you try to locate the 2nd, 3rd, etc... element, a new type of element must be used which keeps track of the index you are looking for and how many times equal has been called. And the hashlookup needs to be disabled, to allow this more sophisticated find to work. Not sure there is any other way other than refreshing the entire tree.
The previous idea won't work... Somehow we have to keep track of all the items associated with an element rather than the built-in 1 to 1 mapping. Some other ideas were focused on reworking the associate/disassociate & mapElement/unmapElement which would work in certain circumstances and fail miserably in others. Another easier trick would be to devise a IElementComparer which can detect differences based on the path in the tree. This is also fraught with problems. I will let you know if I see something that may actually work.
Created attachment 10207 [details] The first attempt at fixing this problem I did finally get something to work, but I am not proud about the patch. In the process I learned quite alot, some good, some bad. What is interesting is how expensive this whole operation was versus what it should have been and the interesting issues that are present. Some of the issues: 1. There is a window between the LabelJob thread and the labelComputed thread where the later could remove labels that the former just added. 2. The DebugViewDecoratingLabelProvider assumed that there would only be one element per computed label. 3. The label update operation is somewhat expensive considering you walk the entire variable tree to find those labels that need updating. After computing the labels, another thread rewalks the tree to find the single tree item to update. My patch addresses 2 & 3. Fixing #1 should be relatively easy by just passing the Map between the threads rather than an instance variable. Problem 2 was addressed by switch the Map.remove to a Map.get. Problem 3 was a bit more intriguing. I ended up creating a Proxy which held both the TreeItem and the element. This was passed around rather than the element. The DebugViewDecoratingLabelProvider, DebugViewLabelDecorator and VariablesViewer was enhanced to handle this new Proxy. The provider and decorator learned how to pull out the element when needed othewise the proxy was passed around. The decorator also can now update the TreeItem directly rather than asking the Tree to perform the impossible. Note: This piece of code needs to be wrapped in a SafeRunnable. The VariableViewer was updated to create this new Proxy. Let me know what you think. Its the only way I could do it while not forcing the data of the tree to be unique, or just walking the tree to find all matching elements. There are some other optimizations that could be done when there are duplicate Proxies with the same data, like shove all the TreeItems into one Proxy.
Do not intend to fix in M9. Marking as 3.0.
Deferred, will put in release notes
The problem has changed in 3.1- see bug 98147. Re-opening to mark as dup.
*** This bug has been marked as a duplicate of 98147 ***