1 /*******************************************************************************
2 * Copyright (c) 2000, 2003 IBM Corporation and others.
3 * All rights reserved. This program and the accompanying materials
4 * are made available under the terms of the Common Public License v1.0
5 * which accompanies this distribution, and is available at
6 * http://www.eclipse.org/legal/cpl-v10.html
9 * IBM Corporation - initial API and implementation
10 *******************************************************************************/
11 package net.sourceforge.phpdt.internal.core;
13 import java.util.ArrayList;
14 import java.util.HashMap;
17 import net.sourceforge.phpdt.core.IBuffer;
18 import net.sourceforge.phpdt.core.IBufferFactory;
19 import net.sourceforge.phpdt.core.ICompilationUnit;
20 import net.sourceforge.phpdt.core.IImportContainer;
21 import net.sourceforge.phpdt.core.IImportDeclaration;
22 import net.sourceforge.phpdt.core.IJavaElement;
23 import net.sourceforge.phpdt.core.IJavaModelStatusConstants;
24 import net.sourceforge.phpdt.core.IJavaProject;
25 import net.sourceforge.phpdt.core.IMember;
26 import net.sourceforge.phpdt.core.IMethod;
27 import net.sourceforge.phpdt.core.IOpenable;
28 import net.sourceforge.phpdt.core.IPackageDeclaration;
29 import net.sourceforge.phpdt.core.IPackageFragmentRoot;
30 import net.sourceforge.phpdt.core.IParent;
31 import net.sourceforge.phpdt.core.IProblemRequestor;
32 import net.sourceforge.phpdt.core.ISourceManipulation;
33 import net.sourceforge.phpdt.core.ISourceRange;
34 import net.sourceforge.phpdt.core.ISourceReference;
35 import net.sourceforge.phpdt.core.IType;
36 import net.sourceforge.phpdt.core.IWorkingCopy;
37 import net.sourceforge.phpdt.core.JavaModelException;
38 import net.sourceforge.phpdt.core.Signature;
39 import net.sourceforge.phpdt.core.WorkingCopyOwner;
40 import net.sourceforge.phpdt.core.compiler.CharOperation;
41 import net.sourceforge.phpdt.core.jdom.IDOMNode;
42 import net.sourceforge.phpdt.internal.compiler.IProblemFactory;
43 import net.sourceforge.phpdt.internal.compiler.SourceElementParser;
44 import net.sourceforge.phpdt.internal.compiler.ast.CompilationUnitDeclaration;
45 import net.sourceforge.phpdt.internal.compiler.impl.CompilerOptions;
46 import net.sourceforge.phpdt.internal.compiler.problem.DefaultProblemFactory;
47 import net.sourceforge.phpdt.internal.core.util.MementoTokenizer;
48 import net.sourceforge.phpdt.internal.core.util.Util;
50 import org.eclipse.core.resources.IContainer;
51 import org.eclipse.core.resources.IFile;
52 import org.eclipse.core.resources.IMarker;
53 import org.eclipse.core.resources.IResource;
54 import org.eclipse.core.runtime.IPath;
55 import org.eclipse.core.runtime.IProgressMonitor;
56 import org.eclipse.core.runtime.Path;
59 * @see ICompilationUnit
62 public class CompilationUnit extends Openable implements ICompilationUnit,
63 net.sourceforge.phpdt.internal.compiler.env.ICompilationUnit {
64 public WorkingCopyOwner owner;
67 * Constructs a handle to a compilation unit with the given name in the
68 * specified package for the specified owner
70 * @exception IllegalArgumentException
71 * if the name of the compilation unit does not end with
74 protected CompilationUnit(PackageFragment parent, String name,
75 WorkingCopyOwner owner) {
81 * Accepts the given visitor onto the parsed tree of this compilation unit,
82 * after having runned the name resolution. The visitor's corresponding
83 * <code>visit</code> method is called with the corresponding parse tree.
84 * If the visitor returns <code>true</code>, this method visits this
85 * parse node's members.
89 * @exception JavaModelException
90 * if this method fails. Reasons include:
92 * <li>This element does not exist.</li>
93 * <li>The visitor failed with this exception.</li>
96 // public void accept(IAbstractSyntaxTreeVisitor visitor) throws
97 // JavaModelException {
98 // CompilationUnitVisitor.visit(this, visitor);
101 * @see ICompilationUnit#becomeWorkingCopy(IProblemRequestor,
104 public void becomeWorkingCopy(IProblemRequestor problemRequestor,
105 IProgressMonitor monitor) throws JavaModelException {
106 JavaModelManager manager = JavaModelManager.getJavaModelManager();
107 JavaModelManager.PerWorkingCopyInfo perWorkingCopyInfo = manager
108 .getPerWorkingCopyInfo(this, false/* don't create */,
109 true /* record usage */, null/*
110 * no problem requestor
113 if (perWorkingCopyInfo == null) {
114 // close cu and its children
117 BecomeWorkingCopyOperation operation = new BecomeWorkingCopyOperation(
118 this, problemRequestor);
119 operation.runOperation(monitor);
123 // protected void buildStructure(OpenableElementInfo info, IProgressMonitor
124 // monitor) throws JavaModelException {
126 // if (monitor != null && monitor.isCanceled()) return;
128 // // remove existing (old) infos
131 // HashMap newElements = new HashMap(11);
132 // info.setIsStructureKnown(generateInfos(info, monitor, newElements,
134 // JavaModelManager.getJavaModelManager().getElementsOutOfSynchWithBuffers().remove(this);
135 // for (Iterator iter = newElements.keySet().iterator(); iter.hasNext();) {
136 // IJavaElement key = (IJavaElement) iter.next();
137 // Object value = newElements.get(key);
138 // JavaModelManager.getJavaModelManager().putInfo(key, value);
140 // // add the info for this at the end, to ensure that a getInfo cannot
141 // reply null in case the LRU cache needs
142 // // to be flushed. Might lead to performance issues.
143 // // see PR 1G2K5S7: ITPJCORE:ALL - NPE when accessing source for a binary
145 // JavaModelManager.getJavaModelManager().putInfo(this, info);
147 protected boolean buildStructure(OpenableElementInfo info,
148 final IProgressMonitor pm, Map newElements,
149 IResource underlyingResource) throws JavaModelException {
151 // check if this compilation unit can be opened
152 if (!isWorkingCopy()) { // no check is done on root kind or exclusion
153 // pattern for working copies
154 if ( // ((IPackageFragment)getParent()).getKind() ==
155 // IPackageFragmentRoot.K_BINARY||
156 !isValidCompilationUnit() || !underlyingResource.isAccessible()) {
157 throw newNotPresentException();
161 // prevents reopening of non-primary working copies (they are closed
162 // when they are discarded and should not be reopened)
163 if (!isPrimary() && getPerWorkingCopyInfo() == null) {
164 throw newNotPresentException();
167 CompilationUnitElementInfo unitInfo = (CompilationUnitElementInfo) info;
169 // get buffer contents
170 IBuffer buffer = getBufferManager().getBuffer(CompilationUnit.this);
171 if (buffer == null) {
172 buffer = openBuffer(pm, unitInfo); // open buffer independently
173 // from the info, since we are
176 final char[] contents = buffer == null ? null : buffer.getCharacters();
178 // generate structure and compute syntax problems if needed
179 CompilationUnitStructureRequestor requestor = new CompilationUnitStructureRequestor(
180 this, unitInfo, newElements);
181 JavaModelManager.PerWorkingCopyInfo perWorkingCopyInfo = getPerWorkingCopyInfo();
182 IJavaProject project = getJavaProject();
183 boolean computeProblems = JavaProject.hasJavaNature(project
185 && perWorkingCopyInfo != null && perWorkingCopyInfo.isActive();
186 IProblemFactory problemFactory = new DefaultProblemFactory();
187 Map options = project.getOptions(true);
189 if (underlyingResource == null) {
190 underlyingResource = getResource();
193 SourceElementParser parser = new SourceElementParser(requestor,
194 problemFactory, new CompilerOptions(options));
195 // , true/*report local declarations*/);
196 requestor.parser = parser;
197 CompilationUnitDeclaration unit = parser
198 .parseCompilationUnit(
199 new net.sourceforge.phpdt.internal.compiler.env.ICompilationUnit() {
200 public char[] getContents() {
204 public char[] getMainTypeName() {
205 return CompilationUnit.this.getMainTypeName();
208 public char[][] getPackageName() {
209 return CompilationUnit.this.getPackageName();
212 public char[] getFileName() {
213 return CompilationUnit.this.getFileName();
216 public IResource getResource() {
217 return CompilationUnit.this.getResource();
219 }, true /* full parse to find local elements */);
221 // update timestamp (might be IResource.NULL_STAMP if original does not
224 unitInfo.timestamp = ((IFile) underlyingResource)
225 .getModificationStamp();
226 // compute other problems if needed
227 CompilationUnitDeclaration compilationUnitDeclaration = null;
229 if (computeProblems) {
230 perWorkingCopyInfo.beginReporting();
231 compilationUnitDeclaration = CompilationUnitProblemFinder
232 .process(unit, this, contents, parser, this.owner,
233 perWorkingCopyInfo, problemFactory,
234 false/* don't cleanup cu */, pm);
235 perWorkingCopyInfo.endReporting();
238 // if (info instanceof ASTHolderCUInfo) {
239 // int astLevel = ((ASTHolderCUInfo) info).astLevel;
240 // net.sourceforge.phpdt.core.dom.CompilationUnit cu =
241 // AST.convertCompilationUnit(astLevel, unit, contents, options,
243 // ((ASTHolderCUInfo) info).ast = cu;
246 if (compilationUnitDeclaration != null) {
247 compilationUnitDeclaration.cleanUp();
251 return unitInfo.isStructureKnown();
255 // * @see ICodeAssist#codeComplete(int, ICompletionRequestor)
257 // public void codeComplete(int offset, ICompletionRequestor requestor)
258 // throws JavaModelException {
259 // codeComplete(this, isWorkingCopy() ?
260 // (net.sourceforge.phpdt.internal.compiler.env.ICompilationUnit)
261 // getOriginalElement() : this,
262 // offset, requestor);
265 * @see ICodeAssist#codeSelect(int, int)
267 // public IJavaElement[] codeSelect(int offset, int length) throws
268 // JavaModelException {
269 // return super.codeSelect(this, offset, length);
272 * @see IWorkingCopy#commit(boolean, IProgressMonitor)
274 public void commit(boolean force, IProgressMonitor monitor)
275 throws JavaModelException {
276 commitWorkingCopy(force, monitor);
277 // throw new JavaModelException(new
278 // JavaModelStatus(IJavaModelStatusConstants.INVALID_ELEMENT_TYPES,
283 * @see ICompilationUnit#commitWorkingCopy(boolean, IProgressMonitor)
285 public void commitWorkingCopy(boolean force, IProgressMonitor monitor)
286 throws JavaModelException {
287 CommitWorkingCopyOperation op = new CommitWorkingCopyOperation(this,
289 op.runOperation(monitor);
293 * @see ISourceManipulation#copy(IJavaElement, IJavaElement, String,
294 * boolean, IProgressMonitor)
296 public void copy(IJavaElement container, IJavaElement sibling,
297 String rename, boolean force, IProgressMonitor monitor)
298 throws JavaModelException {
299 if (container == null) {
300 throw new IllegalArgumentException(Util
301 .bind("operation.nullContainer")); //$NON-NLS-1$
303 IJavaElement[] elements = new IJavaElement[] { this };
304 IJavaElement[] containers = new IJavaElement[] { container };
305 String[] renamings = null;
306 if (rename != null) {
307 renamings = new String[] { rename };
309 getJavaModel().copy(elements, containers, null, renamings, force,
314 * Returns a new element info for this element.
316 protected Object createElementInfo() {
317 return new CompilationUnitElementInfo();
321 // * @see ICompilationUnit#createImport(String, IJavaElement,
324 // public IImportDeclaration createImport(String name, IJavaElement sibling,
325 // IProgressMonitor monitor) throws JavaModelException {
326 // CreateImportOperation op = new CreateImportOperation(name, this);
327 // if (sibling != null) {
328 // op.createBefore(sibling);
330 // runOperation(op, monitor);
331 // return getImport(name);
334 * @see ICompilationUnit#createPackageDeclaration(String, IProgressMonitor)
336 public IPackageDeclaration createPackageDeclaration(String name,
337 IProgressMonitor monitor) throws JavaModelException {
339 CreatePackageDeclarationOperation op = new CreatePackageDeclarationOperation(
341 runOperation(op, monitor);
342 return getPackageDeclaration(name);
346 // * @see ICompilationUnit#createType(String, IJavaElement, boolean,
349 // public IType createType(String content, IJavaElement sibling, boolean
350 // force, IProgressMonitor monitor) throws
351 // JavaModelException {
353 // //autogenerate this compilation unit
354 // IPackageFragment pkg = (IPackageFragment) getParent();
355 // String source = ""; //$NON-NLS-1$
356 // if (pkg.getElementName().length() > 0) {
357 // //not the default package...add the package declaration
358 // source = "package " + pkg.getElementName() + ";" +
359 // net.sourceforge.phpdt.internal.compiler.util.ProjectPrefUtil.LINE_SEPARATOR
361 // net.sourceforge.phpdt.internal.compiler.util.ProjectPrefUtil.LINE_SEPARATOR;
362 // //$NON-NLS-1$ //$NON-NLS-2$
364 // CreateCompilationUnitOperation op = new
365 // CreateCompilationUnitOperation(pkg, fName, source, force);
366 // runOperation(op, monitor);
368 // CreateTypeOperation op = new CreateTypeOperation(this, content, force);
369 // if (sibling != null) {
370 // op.createBefore(sibling);
372 // runOperation(op, monitor);
373 // return (IType) op.getResultElements()[0];
376 * @see ISourceManipulation#delete(boolean, IProgressMonitor)
378 public void delete(boolean force, IProgressMonitor monitor)
379 throws JavaModelException {
380 IJavaElement[] elements = new IJavaElement[] { this };
381 getJavaModel().delete(elements, force, monitor);
385 * @see IWorkingCopy#destroy()
388 public void destroy() {
390 discardWorkingCopy();
391 } catch (JavaModelException e) {
397 * @see ICompilationUnit#discardWorkingCopy
399 public void discardWorkingCopy() throws JavaModelException {
400 // discard working copy and its children
401 DiscardWorkingCopyOperation op = new DiscardWorkingCopyOperation(this);
402 op.runOperation(null);
406 * Returns true if this handle represents the same Java element as the given
409 * @see Object#equals(java.lang.Object)
411 public boolean equals(Object obj) {
412 if (!(obj instanceof CompilationUnit))
414 CompilationUnit other = (CompilationUnit) obj;
415 return this.owner.equals(other.owner) && super.equals(obj);
419 * @see JavaElement#equalsDOMNode(IDOMNode)
421 protected boolean equalsDOMNode(IDOMNode node) throws JavaModelException {
422 String name = getElementName();
423 if (node.getNodeType() == IDOMNode.COMPILATION_UNIT && name != null) {
424 String nodeName = node.getName();
425 if (nodeName == null)
427 if (name.equals(nodeName)) {
430 // iterate through all the types inside the receiver and see if
431 // one of them can fit
432 IType[] types = getTypes();
433 String typeNodeName = nodeName.substring(0, nodeName
434 .indexOf(".java")); //$NON-NLS-1$
435 for (int i = 0, max = types.length; i < max; i++) {
436 if (types[i].getElementName().equals(typeNodeName)) {
446 * @see IWorkingCopy#findElements(IJavaElement)
448 public IJavaElement[] findElements(IJavaElement element) {
449 ArrayList children = new ArrayList();
450 while (element != null
451 && element.getElementType() != IJavaElement.COMPILATION_UNIT) {
452 children.add(element);
453 element = element.getParent();
457 IJavaElement currentElement = this;
458 for (int i = children.size() - 1; i >= 0; i--) {
459 IJavaElement child = (IJavaElement) children.get(i);
460 switch (child.getElementType()) {
461 // case IJavaElement.PACKAGE_DECLARATION:
463 // ((ICompilationUnit)currentElement).getPackageDeclaration(child.getElementName());
465 // case IJavaElement.IMPORT_CONTAINER:
467 // ((ICompilationUnit)currentElement).getImportContainer();
469 // case IJavaElement.IMPORT_DECLARATION:
471 // ((IImportContainer)currentElement).getImport(child.getElementName());
473 case IJavaElement.TYPE:
474 if (currentElement.getElementType() == IJavaElement.COMPILATION_UNIT) {
475 currentElement = ((ICompilationUnit) currentElement)
476 .getType(child.getElementName());
478 currentElement = ((IType) currentElement).getType(child
482 // case IJavaElement.INITIALIZER:
484 // ((IType)currentElement).getInitializer(((JavaElement)child).getOccurrenceCount());
486 case IJavaElement.FIELD:
487 currentElement = ((IType) currentElement).getField(child
490 case IJavaElement.METHOD:
491 return ((IType) currentElement).findMethods((IMethod) child);
495 if (currentElement != null && currentElement.exists()) {
496 return new IJavaElement[] { currentElement };
503 * @see IWorkingCopy#findPrimaryType()
505 public IType findPrimaryType() {
506 String typeName = Signature.getQualifier(this.getElementName());
507 IType primaryType = this.getType(typeName);
508 if (primaryType.exists()) {
515 * @see IWorkingCopy#findSharedWorkingCopy(IBufferFactory)
518 public IJavaElement findSharedWorkingCopy(IBufferFactory factory) {
520 // if factory is null, default factory must be used
522 factory = this.getBufferManager().getDefaultBufferFactory();
524 return findWorkingCopy(BufferFactoryWrapper.create(factory));
528 * @see ICompilationUnit#findWorkingCopy(WorkingCopyOwner)
530 public ICompilationUnit findWorkingCopy(WorkingCopyOwner workingCopyOwner) {
531 CompilationUnit cu = new CompilationUnit((PackageFragment) this.parent,
532 getElementName(), workingCopyOwner);
533 if (workingCopyOwner == DefaultWorkingCopyOwner.PRIMARY) {
536 // must be a working copy
537 JavaModelManager.PerWorkingCopyInfo perWorkingCopyInfo = cu
538 .getPerWorkingCopyInfo();
539 if (perWorkingCopyInfo != null) {
540 return perWorkingCopyInfo.getWorkingCopy();
547 // protected boolean generateInfos(OpenableElementInfo info,
548 // IProgressMonitor pm, Map newElements, IResource underlyingResource)
549 // throws JavaModelException {
551 // // if (getParent() instanceof JarPackageFragment) {
552 // // // ignore .java files in jar
553 // // throw newNotPresentException();
555 // // put the info now, because getting the contents requires it
556 // JavaModelManager.getJavaModelManager().putInfo(this, info);
557 // CompilationUnitElementInfo unitInfo = (CompilationUnitElementInfo) info;
559 // // generate structure
560 // CompilationUnitStructureRequestor requestor = new
561 // CompilationUnitStructureRequestor(this, unitInfo, newElements);
562 // IProblemFactory factory = new DefaultProblemFactory();
563 // SourceElementParser parser = new SourceElementParser(requestor, factory,
565 // CompilerOptions(getJavaProject().getOptions(true)));
566 // // SourceElementParser parser = new SourceElementParser(requestor,
568 // requestor.parser = parser;
569 // parser.parseCompilationUnit(this, false);
570 // if (isWorkingCopy()) {
571 // CompilationUnit original = (CompilationUnit) getOriginalElement();
572 // // might be IResource.NULL_STAMP if original does not exist
573 // unitInfo.timestamp = ((IFile)
574 // original.getResource()).getModificationStamp();
576 // return unitInfo.isStructureKnown();
580 * @see ICompilationUnit#getAllTypes()
582 public IType[] getAllTypes() throws JavaModelException {
583 IJavaElement[] types = getTypes();
585 ArrayList allTypes = new ArrayList(types.length);
586 ArrayList typesToTraverse = new ArrayList(types.length);
587 for (i = 0; i < types.length; i++) {
588 typesToTraverse.add(types[i]);
590 while (!typesToTraverse.isEmpty()) {
591 IType type = (IType) typesToTraverse.get(0);
592 typesToTraverse.remove(type);
594 types = type.getTypes();
595 for (i = 0; i < types.length; i++) {
596 typesToTraverse.add(types[i]);
599 IType[] arrayOfAllTypes = new IType[allTypes.size()];
600 allTypes.toArray(arrayOfAllTypes);
601 return arrayOfAllTypes;
605 * @see IMember#getCompilationUnit()
607 public ICompilationUnit getCompilationUnit() {
612 * @see net.sourceforge.phpdt.internal.compiler.env.ICompilationUnit#getContents()
614 public char[] getContents() {
616 IBuffer buffer = this.getBuffer();
617 return buffer == null ? null : buffer.getCharacters();
618 } catch (JavaModelException e) {
619 return CharOperation.NO_CHAR;
624 * A compilation unit has a corresponding resource unless it is contained in
627 * @see IJavaElement#getCorrespondingResource()
629 public IResource getCorrespondingResource() throws JavaModelException {
630 IPackageFragmentRoot root = (IPackageFragmentRoot) getParent()
632 if (root.isArchive()) {
635 return getUnderlyingResource();
640 * @see ICompilationUnit#getElementAt(int)
642 public IJavaElement getElementAt(int position) throws JavaModelException {
644 IJavaElement e = getSourceElementAt(position);
655 public int getElementType() {
656 return COMPILATION_UNIT;
659 public char[] getFileName() {
660 return getElementName().toCharArray();
666 public IJavaElement getHandleFromMemento(String token,
667 MementoTokenizer memento, WorkingCopyOwner workingCopyOwner) {
668 switch (token.charAt(0)) {
670 return getHandleUpdatingCountFromMemento(memento, workingCopyOwner);
671 case JEM_IMPORTDECLARATION:
672 JavaElement container = (JavaElement) getImportContainer();
673 return container.getHandleFromMemento(token, memento,
675 case JEM_PACKAGEDECLARATION:
676 String pkgName = memento.nextToken();
677 JavaElement pkgDecl = (JavaElement) getPackageDeclaration(pkgName);
678 return pkgDecl.getHandleFromMemento(memento, workingCopyOwner);
680 String typeName = memento.nextToken();
681 JavaElement type = (JavaElement) getType(typeName);
682 return type.getHandleFromMemento(memento, workingCopyOwner);
688 * @see JavaElement#getHandleMementoDelimiter()
690 protected char getHandleMementoDelimiter() {
691 return JavaElement.JEM_COMPILATIONUNIT;
695 * @see ICompilationUnit#getImport(String)
697 public IImportDeclaration getImport(String importName) {
698 return new ImportDeclaration((ImportContainer) getImportContainer(),
703 * @see ICompilationUnit#getImportContainer()
705 public IImportContainer getImportContainer() {
706 return new ImportContainer(this);
710 * @see ICompilationUnit#getImports()
712 public IImportDeclaration[] getImports() throws JavaModelException {
713 IImportContainer container = getImportContainer();
714 if (container.exists()) {
715 IJavaElement[] elements = container.getChildren();
716 IImportDeclaration[] imprts = new IImportDeclaration[elements.length];
717 System.arraycopy(elements, 0, imprts, 0, elements.length);
719 } else if (!exists()) {
720 throw newNotPresentException();
722 return new IImportDeclaration[0];
728 * @see net.sourceforge.phpdt.internal.compiler.env.ICompilationUnit#getMainTypeName()
730 public char[] getMainTypeName() {
731 String name = getElementName();
733 name = name.substring(0, name.length() - 5);
734 return name.toCharArray();
738 * @see IWorkingCopy#getOriginal(IJavaElement)
741 public IJavaElement getOriginal(IJavaElement workingCopyElement) {
742 // backward compatibility
743 if (!isWorkingCopy())
745 CompilationUnit cu = (CompilationUnit) workingCopyElement
746 .getAncestor(COMPILATION_UNIT);
747 if (cu == null || !this.owner.equals(cu.owner)) {
751 return workingCopyElement.getPrimaryElement();
755 * @see IWorkingCopy#getOriginalElement()
758 public IJavaElement getOriginalElement() {
759 // backward compatibility
760 if (!isWorkingCopy())
763 return getPrimaryElement();
767 * @see ICompilationUnit#getOwner()
769 public WorkingCopyOwner getOwner() {
770 return isPrimary() || !isWorkingCopy() ? null : this.owner;
774 * @see ICompilationUnit#getPackageDeclaration(String)
776 public IPackageDeclaration getPackageDeclaration(String name) {
777 return new PackageDeclaration(this, name);
781 * @see ICompilationUnit#getPackageDeclarations()
783 public IPackageDeclaration[] getPackageDeclarations()
784 throws JavaModelException {
785 ArrayList list = getChildrenOfType(PACKAGE_DECLARATION);
786 IPackageDeclaration[] array = new IPackageDeclaration[list.size()];
792 * @see net.sourceforge.phpdt.internal.compiler.env.ICompilationUnit#getPackageName()
794 public char[][] getPackageName() {
799 * @see IJavaElement#getPath()
801 public IPath getPath() {
802 PackageFragmentRoot root = this.getPackageFragmentRoot();
803 if (root.isArchive()) {
804 return root.getPath();
806 return this.getParent().getPath().append(this.getElementName());
811 * Returns the per working copy info for the receiver, or null if none
812 * exist. Note: the use count of the per working copy info is NOT
815 public JavaModelManager.PerWorkingCopyInfo getPerWorkingCopyInfo() {
816 return JavaModelManager.getJavaModelManager().getPerWorkingCopyInfo(
817 this, false/* don't create */, false/* don't record usage */,
818 null/* no problem requestor needed */);
822 * @see ICompilationUnit#getPrimary()
824 public ICompilationUnit getPrimary() {
825 return (ICompilationUnit) getPrimaryElement(true);
829 * @see JavaElement#getPrimaryElement(boolean)
831 public IJavaElement getPrimaryElement(boolean checkOwner) {
832 if (checkOwner && isPrimary())
834 return new CompilationUnit((PackageFragment) getParent(),
835 getElementName(), DefaultWorkingCopyOwner.PRIMARY);
839 * @see IJavaElement#getResource()
841 public IResource getResource() {
842 PackageFragmentRoot root = this.getPackageFragmentRoot();
843 if (root.isArchive()) {
844 return root.getResource();
846 return ((IContainer) this.getParent().getResource())
847 .getFile(new Path(this.getElementName()));
852 * @see ISourceReference#getSource()
854 public String getSource() throws JavaModelException {
855 IBuffer buffer = getBuffer();
857 return ""; //$NON-NLS-1$
858 return buffer.getContents();
862 * @see ISourceReference#getSourceRange()
864 public ISourceRange getSourceRange() throws JavaModelException {
865 return ((CompilationUnitElementInfo) getElementInfo()).getSourceRange();
869 * @see ICompilationUnit#getType(String)
871 public IType getType(String name) {
872 return new SourceType(this, name);
876 * @see ICompilationUnit#getTypes()
878 public IType[] getTypes() throws JavaModelException {
879 ArrayList list = getChildrenOfType(TYPE);
880 IType[] array = new IType[list.size()];
888 public IResource getUnderlyingResource() throws JavaModelException {
889 if (isWorkingCopy() && !isPrimary())
891 return super.getUnderlyingResource();
895 // * @see IWorkingCopy#getSharedWorkingCopy(IProgressMonitor,
896 // IBufferFactory, IProblemRequestor)
898 // public IJavaElement getSharedWorkingCopy(IProgressMonitor pm,
899 // IBufferFactory factory, IProblemRequestor problemRequestor)
900 // throws JavaModelException {
902 // // if factory is null, default factory must be used
903 // if (factory == null) factory =
904 // this.getBufferManager().getDefaultBufferFactory();
906 // JavaModelManager manager = JavaModelManager.getJavaModelManager();
908 // // In order to be shared, working copies have to denote the same
910 // // AND use the same buffer factory.
911 // // Assuming there is a little set of buffer factories, then use a 2 level
913 // Map sharedWorkingCopies = manager.sharedWorkingCopies;
915 // Map perFactoryWorkingCopies = (Map) sharedWorkingCopies.get(factory);
916 // if (perFactoryWorkingCopies == null){
917 // perFactoryWorkingCopies = new HashMap();
918 // sharedWorkingCopies.put(factory, perFactoryWorkingCopies);
920 // WorkingCopy workingCopy = (WorkingCopy)perFactoryWorkingCopies.get(this);
921 // if (workingCopy != null) {
922 // workingCopy.useCount++;
924 // if (SHARED_WC_VERBOSE) {
925 // System.out.println("Incrementing use count of shared working copy " +
926 // workingCopy.toStringWithAncestors()); //$NON-NLS-1$
929 // return workingCopy;
931 // CreateWorkingCopyOperation op = new CreateWorkingCopyOperation(this,
932 // perFactoryWorkingCopies, factory, problemRequestor);
933 // runOperation(op, pm);
934 // return op.getResultElements()[0];
938 // * @see IWorkingCopy#getWorkingCopy()
940 // public IJavaElement getWorkingCopy() throws JavaModelException {
941 // return this.getWorkingCopy(null, null, null);
945 // * @see IWorkingCopy#getWorkingCopy(IProgressMonitor, IBufferFactory,
946 // IProblemRequestor)
948 // public IJavaElement getWorkingCopy(IProgressMonitor pm, IBufferFactory
949 // factory, IProblemRequestor problemRequestor) throws
950 // JavaModelException {
951 // CreateWorkingCopyOperation op = new CreateWorkingCopyOperation(this,
952 // null, factory, problemRequestor);
953 // runOperation(op, pm);
954 // return op.getResultElements()[0];
957 * @see IWorkingCopy#getSharedWorkingCopy(IProgressMonitor, IBufferFactory,
961 public IJavaElement getSharedWorkingCopy(IProgressMonitor pm,
962 IBufferFactory factory, IProblemRequestor problemRequestor)
963 throws JavaModelException {
965 // if factory is null, default factory must be used
967 factory = this.getBufferManager().getDefaultBufferFactory();
969 return getWorkingCopy(BufferFactoryWrapper.create(factory),
970 problemRequestor, pm);
974 * @see IWorkingCopy#getWorkingCopy()
977 public IJavaElement getWorkingCopy() throws JavaModelException {
978 return getWorkingCopy(null);
982 * @see ICompilationUnit#getWorkingCopy(IProgressMonitor)
984 public ICompilationUnit getWorkingCopy(IProgressMonitor monitor)
985 throws JavaModelException {
986 return getWorkingCopy(new WorkingCopyOwner() {/*
990 }, null/* no problem requestor */, monitor);
994 * @see IWorkingCopy#getWorkingCopy(IProgressMonitor, IBufferFactory,
998 public IJavaElement getWorkingCopy(IProgressMonitor monitor,
999 IBufferFactory factory, IProblemRequestor problemRequestor)
1000 throws JavaModelException {
1001 return getWorkingCopy(BufferFactoryWrapper.create(factory),
1002 problemRequestor, monitor);
1006 * @see ICompilationUnit#getWorkingCopy(WorkingCopyOwner, IProblemRequestor,
1009 public ICompilationUnit getWorkingCopy(WorkingCopyOwner workingCopyOwner,
1010 IProblemRequestor problemRequestor, IProgressMonitor monitor)
1011 throws JavaModelException {
1015 JavaModelManager manager = JavaModelManager.getJavaModelManager();
1017 CompilationUnit workingCopy = new CompilationUnit(
1018 (PackageFragment) getParent(), getElementName(),
1020 JavaModelManager.PerWorkingCopyInfo perWorkingCopyInfo = manager
1021 .getPerWorkingCopyInfo(workingCopy, false/* don't create */,
1022 true/* record usage */, null/*
1023 * not used since don't
1026 if (perWorkingCopyInfo != null) {
1027 return perWorkingCopyInfo.getWorkingCopy(); // return existing
1028 // handle instead of the
1029 // one created above
1031 BecomeWorkingCopyOperation op = new BecomeWorkingCopyOperation(
1032 workingCopy, problemRequestor);
1033 op.runOperation(monitor);
1038 * If I am not open, return true to avoid parsing.
1040 * @see IParent#hasChildren()
1042 public boolean hasChildren() throws JavaModelException {
1044 // return getChildren().length > 0;
1052 * @see Openable#hasBuffer()
1054 protected boolean hasBuffer() {
1059 * @see ICompilationUnit#hasResourceChanged()
1061 public boolean hasResourceChanged() {
1062 if (!isWorkingCopy())
1065 // if resource got deleted, then #getModificationStamp() will answer
1066 // IResource.NULL_STAMP, which is always different from the
1069 Object info = JavaModelManager.getJavaModelManager().getInfo(this);
1072 return ((CompilationUnitElementInfo) info).timestamp != getResource()
1073 .getModificationStamp();
1077 * @see IWorkingCopy#isBasedOn(IResource)
1080 public boolean isBasedOn(IResource resource) {
1081 if (!isWorkingCopy())
1083 if (!getResource().equals(resource))
1085 return !hasResourceChanged();
1089 * @see IOpenable#isConsistent()
1091 public boolean isConsistent() {
1092 return JavaModelManager.getJavaModelManager()
1093 .getElementsOutOfSynchWithBuffers().get(this) == null;
1100 public boolean isOpen() {
1101 Object info = JavaModelManager.getJavaModelManager().getInfo(this);
1102 return info != null && ((CompilationUnitElementInfo) info).isOpen();
1105 public boolean isPrimary() {
1106 return this.owner == DefaultWorkingCopyOwner.PRIMARY;
1110 * @see Openable#isSourceElement()
1112 protected boolean isSourceElement() {
1116 protected boolean isValidCompilationUnit() {
1117 IPackageFragmentRoot root = getPackageFragmentRoot();
1119 if (root.getKind() != IPackageFragmentRoot.K_SOURCE)
1121 } catch (JavaModelException e) {
1124 // IResource resource = getResource();
1125 // if (resource != null) {
1126 // char[][] inclusionPatterns =
1127 // ((PackageFragmentRoot)root).fullInclusionPatternChars();
1128 // char[][] exclusionPatterns =
1129 // ((PackageFragmentRoot)root).fullExclusionPatternChars();
1130 // if (ProjectPrefUtil.isExcluded(resource, inclusionPatterns,
1131 // exclusionPatterns)) return false;
1133 if (!Util.isValidCompilationUnitName(getElementName()))
1139 * @see ICompilationUnit#isWorkingCopy()
1141 public boolean isWorkingCopy() {
1142 // For backward compatibility, non primary working copies are always
1143 // returning true; in removal
1144 // delta, clients can still check that element was a working copy before
1146 return !isPrimary() || getPerWorkingCopyInfo() != null;
1150 * @see IOpenable#makeConsistent(IProgressMonitor)
1152 public void makeConsistent(IProgressMonitor monitor)
1153 throws JavaModelException {
1154 makeConsistent(false/* don't create AST */, 0, monitor);
1157 public Object makeConsistent(boolean createAST, int astLevel,
1158 IProgressMonitor monitor) throws JavaModelException {
1162 // create a new info and make it the current info
1163 // (this will remove the info and its children just before storing the
1166 // ASTHolderCUInfo info = new ASTHolderCUInfo();
1167 // info.astLevel = astLevel;
1168 // openWhenClosed(info, monitor);
1169 // net.sourceforge.phpdt.core.dom.CompilationUnit result = info.ast;
1173 openWhenClosed(createElementInfo(), monitor);
1178 // public net.sourceforge.phpdt.core.dom.CompilationUnit
1179 // makeConsistent(boolean createAST, int astLevel, IProgressMonitor monitor)
1180 // throws JavaModelException {
1181 // if (isConsistent()) return null;
1183 // // create a new info and make it the current info
1184 // // (this will remove the info and its children just before storing the
1187 // ASTHolderCUInfo info = new ASTHolderCUInfo();
1188 // info.astLevel = astLevel;
1189 // openWhenClosed(info, monitor);
1190 // net.sourceforge.phpdt.core.dom.CompilationUnit result = info.ast;
1194 // openWhenClosed(createElementInfo(), monitor);
1200 * @see ISourceManipulation#move(IJavaElement, IJavaElement, String,
1201 * boolean, IProgressMonitor)
1203 public void move(IJavaElement container, IJavaElement sibling,
1204 String rename, boolean force, IProgressMonitor monitor)
1205 throws JavaModelException {
1206 if (container == null) {
1207 throw new IllegalArgumentException(Util
1208 .bind("operation.nullContainer")); //$NON-NLS-1$
1210 IJavaElement[] elements = new IJavaElement[] { this };
1211 IJavaElement[] containers = new IJavaElement[] { container };
1213 String[] renamings = null;
1214 if (rename != null) {
1215 renamings = new String[] { rename };
1217 getJavaModel().move(elements, containers, null, renamings, force,
1222 // * @see Openable#openBuffer(IProgressMonitor)
1224 // protected IBuffer openBuffer(IProgressMonitor pm) throws
1225 // JavaModelException {
1227 // // create buffer - compilation units only use default buffer factory
1228 // BufferManager bufManager = getBufferManager();
1229 // IBuffer buffer = getBufferFactory().createBuffer(this);
1230 // if (buffer == null) return null;
1232 // // set the buffer source
1233 // if (buffer.getCharacters() == null){
1234 // IFile file = (IFile)this.getResource();
1235 // if (file == null || !file.exists()) throw newNotPresentException();
1236 // buffer.setContents(ProjectPrefUtil.getResourceContentsAsCharArray(file));
1239 // // add buffer to buffer cache
1240 // bufManager.addBuffer(buffer);
1242 // // listen to buffer changes
1243 // buffer.addBufferChangedListener(this);
1248 * @see Openable#openBuffer(IProgressMonitor, Object)
1250 protected IBuffer openBuffer(IProgressMonitor pm, Object info)
1251 throws JavaModelException {
1254 boolean isWorkingCopy = isWorkingCopy();
1255 IBuffer buffer = isWorkingCopy ? this.owner.createBuffer(this)
1256 : BufferManager.getDefaultBufferManager().createBuffer(this);
1260 // set the buffer source
1261 if (buffer.getCharacters() == null) {
1262 if (isWorkingCopy) {
1263 ICompilationUnit original;
1265 && (original = new CompilationUnit(
1266 (PackageFragment) getParent(),
1268 DefaultWorkingCopyOwner.PRIMARY)).isOpen()) {
1269 buffer.setContents(original.getSource());
1271 IFile file = (IFile) getResource();
1272 if (file == null || !file.exists()) {
1273 // initialize buffer with empty contents
1274 buffer.setContents(CharOperation.NO_CHAR);
1276 buffer.setContents(Util
1277 .getResourceContentsAsCharArray(file));
1281 IFile file = (IFile) this.getResource();
1282 if (file == null || !file.exists())
1283 throw newNotPresentException();
1284 buffer.setContents(Util.getResourceContentsAsCharArray(file));
1288 // add buffer to buffer cache
1289 BufferManager bufManager = getBufferManager();
1290 bufManager.addBuffer(buffer);
1292 // listen to buffer changes
1293 buffer.addBufferChangedListener(this);
1299 * @see Openable#openParent
1301 protected void openParent(Object childInfo, HashMap newElements,
1302 IProgressMonitor pm) throws JavaModelException {
1304 super.openParent(childInfo, newElements, pm);
1305 } catch (JavaModelException e) {
1306 // allow parent to not exist for working copies defined outside
1308 if (!isWorkingCopy() && !e.isDoesNotExist()) {
1315 * @see ICompilationUnit#reconcile()
1318 public IMarker[] reconcile() throws JavaModelException {
1319 reconcile(NO_AST, false/* don't force problem detection */,
1320 null/* use primary owner */, null/* no progress monitor */);
1325 * @see ICompilationUnit#reconcile(int, boolean, WorkingCopyOwner,
1328 public void reconcile(boolean forceProblemDetection,
1329 IProgressMonitor monitor) throws JavaModelException {
1330 reconcile(NO_AST, forceProblemDetection, null/* use primary owner */,
1335 * @see ICompilationUnit#reconcile(int, boolean, WorkingCopyOwner,
1339 // public net.sourceforge.phpdt.core.dom.CompilationUnit reconcile(
1340 public Object reconcile(int astLevel, boolean forceProblemDetection,
1341 WorkingCopyOwner workingCopyOwner, IProgressMonitor monitor)
1342 throws JavaModelException {
1344 if (!isWorkingCopy())
1345 return null; // Reconciling is not supported on non working
1347 if (workingCopyOwner == null)
1348 workingCopyOwner = DefaultWorkingCopyOwner.PRIMARY;
1350 boolean createAST = false;
1351 // if (astLevel == AST.JLS2) {
1352 // // client asking for level 2 AST; these are supported
1353 // createAST = true;
1354 // } else if (astLevel == AST.JLS3) {
1355 // // client asking for level 3 ASTs; these are not supported
1356 // // TODO (jerome) - these should also be supported in 1.5 stream
1357 // createAST = false;
1359 // // client asking for no AST (0) or unknown ast level
1360 // // either way, request denied
1361 // createAST = false;
1363 ReconcileWorkingCopyOperation op = new ReconcileWorkingCopyOperation(
1364 this, createAST, astLevel, forceProblemDetection,
1366 op.runOperation(monitor);
1372 * @see ISourceManipulation#rename(String, boolean, IProgressMonitor)
1374 public void rename(String name, boolean force, IProgressMonitor monitor)
1375 throws JavaModelException {
1377 throw new IllegalArgumentException(Util.bind("operation.nullName")); //$NON-NLS-1$
1379 IJavaElement[] elements = new IJavaElement[] { this };
1380 IJavaElement[] dests = new IJavaElement[] { this.getParent() };
1381 String[] renamings = new String[] { name };
1382 getJavaModel().rename(elements, dests, renamings, force, monitor);
1386 * @see ICompilationUnit
1388 public void restore() throws JavaModelException {
1390 if (!isWorkingCopy())
1393 CompilationUnit original = (CompilationUnit) getOriginalElement();
1394 IBuffer buffer = this.getBuffer();
1397 buffer.setContents(original.getContents());
1398 updateTimeStamp(original);
1399 makeConsistent(null);
1403 // * @see ICodeAssist#codeComplete(int, ICodeCompletionRequestor)
1404 // * @deprecated - use codeComplete(int, ICompletionRequestor)
1406 // public void codeComplete(int offset, final ICodeCompletionRequestor
1407 // requestor) throws JavaModelException {
1409 // if (requestor == null){
1410 // codeComplete(offset, (ICompletionRequestor)null);
1415 // new ICompletionRequestor(){
1416 // public void acceptAnonymousType(char[] superTypePackageName,char[]
1417 // superTypeName,char[][] parameterPackageNames,char[][]
1418 // parameterTypeNames,char[][] parameterNames,char[] completionName,int
1419 // modifiers,int completionStart,int completionEnd, int
1422 // public void acceptClass(char[] packageName, char[] className, char[]
1423 // completionName, int modifiers, int completionStart, int
1424 // completionEnd, int relevance) {
1425 // requestor.acceptClass(packageName, className, completionName, modifiers,
1426 // completionStart, completionEnd);
1428 // public void acceptError(IProblem error) {
1429 // if (true) return; // was disabled in 1.0
1433 // ResourcesPlugin.getWorkspace().getRoot().createMarker(IJavaModelMarker.TRANSIENT_PROBLEM);
1434 // marker.setAttribute(IJavaModelMarker.ID, error.getID());
1435 // marker.setAttribute(IMarker.CHAR_START, error.getSourceStart());
1436 // marker.setAttribute(IMarker.CHAR_END, error.getSourceEnd() + 1);
1437 // marker.setAttribute(IMarker.LINE_NUMBER, error.getSourceLineNumber());
1438 // marker.setAttribute(IMarker.MESSAGE, error.getMessage());
1439 // marker.setAttribute(IMarker.SEVERITY, IMarker.SEVERITY_ERROR);
1440 // requestor.acceptError(marker);
1441 // } catch(CoreException e){
1444 // public void acceptField(char[] declaringTypePackageName, char[]
1445 // declaringTypeName, char[] name, char[] typePackageName, char[]
1446 // typeName, char[] completionName, int modifiers, int completionStart, int
1447 // completionEnd, int relevance) {
1448 // requestor.acceptField(declaringTypePackageName, declaringTypeName, name,
1449 // typePackageName, typeName, completionName, modifiers,
1450 // completionStart, completionEnd);
1452 // public void acceptInterface(char[] packageName,char[]
1453 // interfaceName,char[] completionName,int modifiers,int completionStart,int
1454 // completionEnd, int relevance) {
1455 // requestor.acceptInterface(packageName, interfaceName, completionName,
1456 // modifiers, completionStart, completionEnd);
1458 // public void acceptKeyword(char[] keywordName,int completionStart,int
1459 // completionEnd, int relevance){
1460 // requestor.acceptKeyword(keywordName, completionStart, completionEnd);
1462 // public void acceptLabel(char[] labelName,int completionStart,int
1463 // completionEnd, int relevance){
1464 // requestor.acceptLabel(labelName, completionStart, completionEnd);
1466 // public void acceptLocalVariable(char[] name,char[] typePackageName,char[]
1467 // typeName,int modifiers,int completionStart,int
1468 // completionEnd, int relevance){
1471 // public void acceptMethod(char[] declaringTypePackageName,char[]
1472 // declaringTypeName,char[] selector,char[][]
1473 // parameterPackageNames,char[][] parameterTypeNames,char[][]
1474 // parameterNames,char[] returnTypePackageName,char[]
1475 // returnTypeName,char[] completionName,int modifiers,int
1476 // completionStart,int completionEnd, int relevance){
1477 // // skip parameter names
1478 // requestor.acceptMethod(declaringTypePackageName, declaringTypeName,
1479 // selector, parameterPackageNames, parameterTypeNames,
1480 // returnTypePackageName, returnTypeName, completionName, modifiers,
1481 // completionStart, completionEnd);
1483 // public void acceptMethodDeclaration(char[]
1484 // declaringTypePackageName,char[] declaringTypeName,char[]
1485 // selector,char[][]
1486 // parameterPackageNames,char[][] parameterTypeNames,char[][]
1487 // parameterNames,char[] returnTypePackageName,char[]
1488 // returnTypeName,char[] completionName,int modifiers,int
1489 // completionStart,int completionEnd, int relevance){
1492 // public void acceptModifier(char[] modifierName,int completionStart,int
1493 // completionEnd, int relevance){
1494 // requestor.acceptModifier(modifierName, completionStart, completionEnd);
1496 // public void acceptPackage(char[] packageName,char[] completionName,int
1497 // completionStart,int completionEnd, int relevance){
1498 // requestor.acceptPackage(packageName, completionName, completionStart,
1501 // public void acceptType(char[] packageName,char[] typeName,char[]
1502 // completionName,int completionStart,int completionEnd, int
1504 // requestor.acceptType(packageName, typeName, completionName,
1505 // completionStart, completionEnd);
1507 // public void acceptVariableName(char[] typePackageName,char[]
1508 // typeName,char[] name,char[] completionName,int completionStart,int
1509 // completionEnd, int relevance){
1515 // * @see JavaElement#rootedAt(IJavaProject)
1517 // public IJavaElement rootedAt(IJavaProject project) {
1519 // new CompilationUnit(
1520 // (IPackageFragment)((JavaElement)parent).rootedAt(project),
1525 * Assume that this is a working copy
1527 protected void updateTimeStamp(CompilationUnit original)
1528 throws JavaModelException {
1529 long timeStamp = ((IFile) original.getResource())
1530 .getModificationStamp();
1531 if (timeStamp == IResource.NULL_STAMP) {
1532 throw new JavaModelException(new JavaModelStatus(
1533 IJavaModelStatusConstants.INVALID_RESOURCE));
1535 ((CompilationUnitElementInfo) getElementInfo()).timestamp = timeStamp;