Mercurial > hg > graal-compiler
comparison graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/compiler/JDTCompiler.java @ 16753:f78eafd5ba9e
Truffle-DSL: the processor compiler abstraction now supports declaration oder for enclosed elements of types for JDT which is not conforming to specification.
author | Christian Humer <christian.humer@gmail.com> |
---|---|
date | Mon, 11 Aug 2014 15:53:05 +0200 |
parents | ae6b8ec920e2 |
children |
comparison
equal
deleted
inserted
replaced
16752:0e05342037d7 | 16753:f78eafd5ba9e |
---|---|
24 | 24 |
25 import java.util.*; | 25 import java.util.*; |
26 | 26 |
27 import javax.annotation.processing.*; | 27 import javax.annotation.processing.*; |
28 import javax.lang.model.element.*; | 28 import javax.lang.model.element.*; |
29 import javax.lang.model.type.*; | |
29 | 30 |
30 import com.oracle.truffle.dsl.processor.*; | 31 import com.oracle.truffle.dsl.processor.*; |
31 | 32 |
32 public class JDTCompiler extends AbstractCompiler { | 33 public class JDTCompiler extends AbstractCompiler { |
33 | 34 |
38 } catch (ClassNotFoundException e) { | 39 } catch (ClassNotFoundException e) { |
39 return false; | 40 return false; |
40 } | 41 } |
41 } | 42 } |
42 | 43 |
43 public List<? extends Element> getEnclosedElementsDeclarationOrder(TypeElement type) { | 44 public List<? extends Element> getAllMembersInDeclarationOrder(ProcessingEnvironment environment, TypeElement type) { |
44 try { | 45 return sortBySourceOrder(new ArrayList<>(environment.getElementUtils().getAllMembers(type))); |
45 Object binding = field(type, "_binding"); | 46 } |
46 | 47 |
47 Class<?> sourceTypeBinding = Class.forName("org.eclipse.jdt.internal.compiler.lookup.SourceTypeBinding"); | 48 public List<? extends Element> getEnclosedElementsInDeclarationOrder(TypeElement type) { |
48 | 49 return sortBySourceOrder(new ArrayList<>(type.getEnclosedElements())); |
49 final List<Object> declarationOrder; | 50 } |
50 if (sourceTypeBinding.isAssignableFrom(binding.getClass())) { | 51 |
51 declarationOrder = findSourceOrder(binding); | 52 private static List<? extends Element> sortBySourceOrder(List<Element> elements) { |
52 } else { | 53 final Map<TypeElement, List<Object>> declarationOrders = new HashMap<>(); |
53 return null; | 54 |
54 } | 55 Collections.sort(elements, new Comparator<Element>() { |
55 | 56 public int compare(Element o1, Element o2) { |
56 List<Element> enclosedElements = new ArrayList<>(type.getEnclosedElements()); | 57 try { |
57 Collections.sort(enclosedElements, new Comparator<Element>() { | 58 TypeMirror enclosing1 = o1.getEnclosingElement().asType(); |
58 | 59 TypeMirror enclosing2 = o2.getEnclosingElement().asType(); |
59 public int compare(Element o1, Element o2) { | 60 |
60 try { | 61 if (Utils.typeEquals(enclosing1, enclosing2)) { |
62 List<Object> declarationOrder = lookupDeclarationOrder(declarationOrders, (TypeElement) o1.getEnclosingElement()); | |
63 if (declarationOrder == null) { | |
64 return 0; | |
65 } | |
61 Object o1Binding = field(o1, "_binding"); | 66 Object o1Binding = field(o1, "_binding"); |
62 Object o2Binding = field(o2, "_binding"); | 67 Object o2Binding = field(o2, "_binding"); |
63 | 68 |
64 int i1 = declarationOrder.indexOf(o1Binding); | 69 int i1 = declarationOrder.indexOf(o1Binding); |
65 int i2 = declarationOrder.indexOf(o2Binding); | 70 int i2 = declarationOrder.indexOf(o2Binding); |
66 | 71 |
67 return i1 - i2; | 72 return i1 - i2; |
68 } catch (Exception e) { | 73 } else { |
69 return 0; | 74 if (Utils.isSubtype(enclosing1, enclosing2)) { |
75 return 1; | |
76 } else if (Utils.isSubtype(enclosing2, enclosing1)) { | |
77 return -1; | |
78 } else { | |
79 return 0; | |
80 } | |
70 } | 81 } |
71 } | 82 } catch (Exception e) { |
72 | 83 throw new RuntimeException(e); |
73 }); | 84 } |
74 return enclosedElements; | 85 } |
75 } catch (Exception e) { | 86 }); |
76 return null; | 87 return elements; |
77 } | 88 } |
78 } | 89 |
79 | 90 private static List<Object> lookupDeclarationOrder(Map<TypeElement, List<Object>> declarationOrders, TypeElement type) throws Exception, ClassNotFoundException { |
80 private static List<Object> findSourceOrder(Object binding) throws Exception { | 91 if (declarationOrders.containsKey(type)) { |
92 return declarationOrders.get(type); | |
93 } | |
94 | |
95 Object binding = field(type, "_binding"); | |
96 Class<?> sourceTypeBinding = Class.forName("org.eclipse.jdt.internal.compiler.lookup.SourceTypeBinding"); | |
97 Class<?> binaryTypeBinding = Class.forName("org.eclipse.jdt.internal.compiler.lookup.BinaryTypeBinding"); | |
98 | |
99 List<Object> declarationOrder = null; | |
100 if (sourceTypeBinding.isAssignableFrom(binding.getClass())) { | |
101 declarationOrder = findSourceTypeOrder(binding); | |
102 } else if (binaryTypeBinding.isAssignableFrom(binding.getClass())) { | |
103 declarationOrder = findBinaryTypeOrder(binding); | |
104 } | |
105 | |
106 declarationOrders.put(type, declarationOrder); | |
107 | |
108 return declarationOrder; | |
109 } | |
110 | |
111 private static List<Object> findBinaryTypeOrder(Object binding) throws Exception { | |
112 Object binaryType = lookupBinaryType(binding); | |
113 final Object[] sortedMethods = (Object[]) method(binaryType, "getMethods"); | |
114 | |
115 List<Object> sortedElements = new ArrayList<>(); | |
116 if (sortedMethods != null) { | |
117 sortedElements.addAll(Arrays.asList(sortedMethods)); | |
118 } | |
119 final Object[] sortedFields = (Object[]) method(binaryType, "getFields"); | |
120 if (sortedFields != null) { | |
121 sortedElements.addAll(Arrays.asList(sortedFields)); | |
122 } | |
123 final Object[] sortedTypes = (Object[]) method(binaryType, "getMemberTypes", new Class[0]); | |
124 if (sortedTypes != null) { | |
125 sortedElements.addAll(Arrays.asList(sortedTypes)); | |
126 } | |
127 | |
128 Collections.sort(sortedElements, new Comparator<Object>() { | |
129 public int compare(Object o1, Object o2) { | |
130 try { | |
131 int structOffset1 = (int) field(o1, "structOffset"); | |
132 int structOffset2 = (int) field(o2, "structOffset"); | |
133 return structOffset1 - structOffset2; | |
134 } catch (Exception e) { | |
135 throw new RuntimeException(e); | |
136 } | |
137 } | |
138 }); | |
139 | |
140 Class<?> binaryMethod = Class.forName("org.eclipse.jdt.internal.compiler.env.IBinaryMethod"); | |
141 Class<?> binaryField = Class.forName("org.eclipse.jdt.internal.compiler.env.IBinaryField"); | |
142 Class<?> nestedType = Class.forName("org.eclipse.jdt.internal.compiler.env.IBinaryNestedType"); | |
143 | |
144 List<Object> bindings = new ArrayList<>(); | |
145 for (Object sortedElement : sortedElements) { | |
146 Class<?> elementClass = sortedElement.getClass(); | |
147 if (binaryMethod.isAssignableFrom(elementClass)) { | |
148 char[] selector = (char[]) method(sortedElement, "getSelector"); | |
149 Object[] foundBindings = (Object[]) method(binding, "getMethods", new Class[]{char[].class}, selector); | |
150 if (foundBindings == null || foundBindings.length == 0) { | |
151 continue; | |
152 } else if (foundBindings.length == 1) { | |
153 bindings.add(foundBindings[0]); | |
154 } else { | |
155 char[] idescriptor = (char[]) method(sortedElement, "getMethodDescriptor"); | |
156 for (Object foundBinding : foundBindings) { | |
157 char[] descriptor = (char[]) method(foundBinding, "signature"); | |
158 if (descriptor == null && idescriptor == null || Arrays.equals(descriptor, idescriptor)) { | |
159 bindings.add(foundBinding); | |
160 break; | |
161 } | |
162 } | |
163 } | |
164 } else if (binaryField.isAssignableFrom(elementClass)) { | |
165 char[] selector = (char[]) method(sortedElement, "getName"); | |
166 Object foundField = method(binding, "getField", new Class[]{char[].class, boolean.class}, selector, true); | |
167 if (foundField != null) { | |
168 bindings.add(foundField); | |
169 } | |
170 } else if (nestedType.isAssignableFrom(elementClass)) { | |
171 char[] selector = (char[]) method(sortedElement, "getSourceName"); | |
172 Object foundType = method(binding, "getMemberType", new Class[]{char[].class}, selector); | |
173 if (foundType != null) { | |
174 bindings.add(foundType); | |
175 } | |
176 } else { | |
177 throw new AssertionError("Unexpected encountered type " + elementClass); | |
178 } | |
179 } | |
180 | |
181 return bindings; | |
182 } | |
183 | |
184 private static Object lookupBinaryType(Object binding) throws Exception { | |
185 Object lookupEnvironment = field(binding, "environment"); | |
186 Object compoundClassName = field(binding, "compoundName"); | |
187 Object nameEnvironment = field(lookupEnvironment, "nameEnvironment"); | |
188 Object nameEnvironmentAnswer = method(nameEnvironment, "findType", new Class[]{char[][].class}, compoundClassName); | |
189 Object binaryType = method(nameEnvironmentAnswer, "getBinaryType", new Class[0]); | |
190 return binaryType; | |
191 } | |
192 | |
193 private static List<Object> findSourceTypeOrder(Object binding) throws Exception { | |
81 Object referenceContext = field(field(binding, "scope"), "referenceContext"); | 194 Object referenceContext = field(field(binding, "scope"), "referenceContext"); |
82 | 195 |
83 TreeMap<Integer, Object> orderedBindings = new TreeMap<>(); | 196 TreeMap<Integer, Object> orderedBindings = new TreeMap<>(); |
84 | 197 |
85 collectSourceOrder(orderedBindings, referenceContext, "methods"); | 198 collectSourceOrder(orderedBindings, referenceContext, "methods"); |