You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

EclipseScope.java 7.3KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259
  1. /* *******************************************************************
  2. * Copyright (c) 2002 Palo Alto Research Center, Incorporated (PARC).
  3. * All rights reserved.
  4. * This program and the accompanying materials are made available
  5. * under the terms of the Common Public License v1.0
  6. * which accompanies this distribution and is available at
  7. * http://www.eclipse.org/legal/cpl-v10.html
  8. *
  9. * Contributors:
  10. * Xerox/PARC initial implementation
  11. * ******************************************************************/
  12. package org.aspectj.ajdt.internal.compiler.lookup;
  13. import java.util.*;
  14. import org.aspectj.bridge.*;
  15. import org.aspectj.weaver.*;
  16. import org.aspectj.weaver.patterns.*;
  17. import org.eclipse.jdt.internal.compiler.lookup.*;
  18. import org.eclipse.jdt.internal.compiler.util.CharOperation;
  19. /**
  20. * Adaptor from org.eclipse.jdt.internal.compiler.lookup.Scope to org.aspectj.weaver.IScope
  21. *
  22. * @author Jim Hugunin
  23. */
  24. public class EclipseScope implements IScope {
  25. private Scope scope;
  26. private EclipseWorld world;
  27. private ResolvedTypeX enclosingType;
  28. private FormalBinding[] bindings;
  29. private String[] importedPrefixes = null;
  30. private String[] importedNames = null;
  31. public EclipseScope(FormalBinding[] bindings, Scope scope) {
  32. this.bindings = bindings;
  33. this.scope = scope;
  34. this.world = EclipseWorld.fromScopeLookupEnvironment(scope);
  35. this.enclosingType = world.fromEclipse(scope.enclosingSourceType());
  36. }
  37. public TypeX lookupType(String name, IHasPosition location) {
  38. computeImports();
  39. // System.out.println("lookup: " + name + " in " +
  40. // Arrays.asList(importedPrefixes));
  41. ResolvedTypeX ret = null;
  42. String dotName = "." + name;
  43. for (int i=0; i<importedNames.length; i++) {
  44. String importedName = importedNames[i];
  45. //??? can this be right
  46. if (importedName.endsWith(name) &&
  47. ((importedName.length() == name.length()) ||
  48. (importedName.endsWith(dotName))))
  49. {
  50. ResolvedTypeX found = resolveVisible(importedName);
  51. if (found == ResolvedTypeX.MISSING) continue;
  52. if (ret != null) {
  53. message(IMessage.ERROR, location,
  54. "ambiguous type reference, both " + ret.getName() + " and " + importedName);
  55. return ResolvedTypeX.MISSING;
  56. } else {
  57. ret = found;
  58. }
  59. }
  60. }
  61. if (ret != null) return ret;
  62. //XXX need to handle ambiguous references here
  63. for (int i=0; i<importedPrefixes.length; i++) {
  64. String importedPrefix = importedPrefixes[i];
  65. ResolvedTypeX tryType = resolveVisible(importedPrefix + name);
  66. if (tryType != ResolvedTypeX.MISSING) {
  67. return tryType;
  68. }
  69. }
  70. return resolveVisible(name);
  71. }
  72. private ResolvedTypeX resolveVisible(String name) {
  73. ResolvedTypeX found = world.resolve(TypeX.forName(name), true);
  74. if (found == ResolvedTypeX.MISSING) return found;
  75. if (ResolvedTypeX.isVisible(found.getModifiers(), found, enclosingType)) return found;
  76. return ResolvedTypeX.MISSING;
  77. }
  78. // public TypeX lookupType(String name, IHasPosition location) {
  79. // char[][] namePieces = CharOperation.splitOn('.', name.toCharArray());
  80. // TypeBinding binding;
  81. // if (namePieces.length == 1) {
  82. // binding = scope.getType(namePieces[0]);
  83. // } else {
  84. // binding = scope.getType(namePieces);
  85. // }
  86. //
  87. //
  88. // if (!binding.isValidBinding()) {
  89. // //XXX do we do this always or sometimes
  90. // System.err.println("error: " + binding);
  91. // scope.problemReporter().invalidType(EclipseWorld.astForLocation(location), binding);
  92. // return ResolvedTypeX.MISSING;
  93. // }
  94. // //??? do we want this too
  95. //// if (AstNode.isTypeUseDeprecated(binding, scope))
  96. //// scope.problemReporter().deprecatedType(binding, EclipseWorld.astForLocation(location));
  97. //
  98. // return EclipseWorld.fromBinding(binding);
  99. // }
  100. private void computeImports() {
  101. if (importedNames != null) return;
  102. List importedNamesList = new ArrayList();
  103. List importedPrefixesList = new ArrayList();
  104. Scope currentScope = scope;
  105. //add any enclosing types to this list
  106. while (!(currentScope instanceof CompilationUnitScope)) {
  107. if (currentScope == null) {
  108. throw new RuntimeException("unimplemented");
  109. }
  110. if (currentScope instanceof ClassScope) {
  111. addClassAndParentsToPrefixes(((ClassScope)currentScope).referenceType().binding, importedPrefixesList);
  112. }
  113. currentScope = currentScope.parent;
  114. }
  115. CompilationUnitScope cuScope = (CompilationUnitScope)currentScope;
  116. String packageName =
  117. new String(CharOperation.concatWith(cuScope.currentPackageName, '.'));
  118. if (packageName.length() > 1) {
  119. importedPrefixesList.add(packageName + ".");
  120. }
  121. ImportBinding[] imports = cuScope.imports;
  122. for (int i = 0; i < imports.length; i++) {
  123. ImportBinding importBinding = imports[i];
  124. String importName =
  125. new String(CharOperation.concatWith(importBinding.compoundName, '.'));
  126. //XXX wrong behavior for java.util.Map.*
  127. if (importBinding.onDemand) {
  128. importedPrefixesList.add(importName + ".");
  129. } else {
  130. importedNamesList.add(importName);
  131. }
  132. }
  133. TypeBinding[] topTypes = cuScope.topLevelTypes;
  134. for (int i = 0; i < topTypes.length; i++) {
  135. importedNamesList.add(EclipseWorld.fromBinding(topTypes[i]).getName());
  136. }
  137. importedNames =
  138. (String[])importedNamesList.toArray(new String[importedNamesList.size()]);
  139. importedPrefixes =
  140. (String[])importedPrefixesList.toArray(new String[importedPrefixesList.size()]);
  141. }
  142. private void addClassAndParentsToPrefixes(
  143. ReferenceBinding binding,
  144. List importedPrefixesList)
  145. {
  146. if (binding == null) return;
  147. importedPrefixesList.add(EclipseWorld.fromBinding(binding).getName()+"$");
  148. addClassAndParentsToPrefixes(binding.superclass(), importedPrefixesList);
  149. ReferenceBinding[] superinterfaces = binding.superInterfaces();
  150. if (superinterfaces != null) {
  151. for (int i = 0; i < superinterfaces.length; i++) {
  152. addClassAndParentsToPrefixes(superinterfaces[i], importedPrefixesList);
  153. }
  154. }
  155. }
  156. public String[] getImportedNames() {
  157. computeImports();
  158. return importedNames;
  159. }
  160. public String[] getImportedPrefixes() {
  161. computeImports();
  162. return importedPrefixes;
  163. }
  164. //XXX add good errors when would bind to extra parameters
  165. public FormalBinding lookupFormal(String name) {
  166. for (int i = 0, len = bindings.length; i < len; i++) {
  167. if (bindings[i].getName().equals(name)) return bindings[i];
  168. }
  169. return null;
  170. }
  171. public FormalBinding getFormal(int i) {
  172. return bindings[i];
  173. }
  174. public int getFormalCount() {
  175. return bindings.length;
  176. }
  177. public ISourceLocation makeSourceLocation(IHasPosition location) {
  178. return new EclipseSourceLocation(scope.problemReporter().referenceContext.compilationResult(),
  179. location.getStart(), location.getEnd());
  180. }
  181. public IMessageHandler getMessageHandler() {
  182. return world.getMessageHandler();
  183. }
  184. public void message(
  185. IMessage.Kind kind,
  186. IHasPosition location1,
  187. IHasPosition location2,
  188. String message) {
  189. message(kind, location1, message);
  190. message(kind, location2, message);
  191. }
  192. public void message(
  193. IMessage.Kind kind,
  194. IHasPosition location,
  195. String message) {
  196. //System.out.println("message: " + message + " loc: " + makeSourceLocation(location));
  197. getMessageHandler()
  198. .handleMessage(new Message(message, kind, null, makeSourceLocation(location)));
  199. }
  200. public World getWorld() {
  201. return world;
  202. }
  203. public ResolvedTypeX getEnclosingType() {
  204. return enclosingType;
  205. }
  206. }