EMMA Coverage Report (generated Thu Nov 26 15:54:18 CST 2009)
[all classes][org.eclipse.pde.api.tools.internal.builder]

COVERAGE SUMMARY FOR SOURCE FILE [AbstractProblemDetector.java]

nameclass, %method, %block, %line, %
AbstractProblemDetector.java100% (1/1)80%  (16/20)72%  (647/898)68%  (166.8/245)

COVERAGE BREAKDOWN BY CLASS AND METHOD

nameclass, %method, %block, %line, %
     
class AbstractProblemDetector100% (1/1)80%  (16/20)72%  (647/898)68%  (166.8/245)
createProblem (IReference): IApiProblem 0%   (0/1)0%   (0/44)0%   (0/16)
getQualifiedTypeName (IApiMember): String 0%   (0/1)0%   (0/45)0%   (0/12)
getSourceRangeForField (IType, IReference, IApiField): Position 0%   (0/1)0%   (0/32)0%   (0/9)
setDebug (boolean): void 0%   (0/1)0%   (0/9)0%   (0/2)
getSimpleTypeName (IApiMember): String 100% (1/1)47%  (21/45)50%  (6/12)
findMethodNameStart (String, String, int): int 100% (1/1)77%  (30/39)70%  (7/10)
getMethodNameRange (boolean, String, IDocument, IReference): Position 100% (1/1)83%  (97/117)80%  (24/30)
findMethodInType (IType, IApiMethod): IMethod 100% (1/1)84%  (71/85)89%  (17/19)
getSourceRangeForMethod (IType, IReference, IApiMethod): Position 100% (1/1)84%  (26/31)89%  (8/9)
createProblem (IReference, IJavaProject): IApiProblem 100% (1/1)84%  (137/163)74%  (36.9/50)
isProblem (IReference): boolean 100% (1/1)87%  (27/31)77%  (6.9/9)
createProblems (): List 100% (1/1)87%  (55/63)84%  (16/19)
defaultSourcePosition (IType, IReference): Position 100% (1/1)88%  (15/17)80%  (4/5)
getFieldNameRange (String, String, IDocument, IReference): Position 100% (1/1)92%  (108/117)93%  (26/28)
<static initializer> 100% (1/1)100% (3/3)100% (2/2)
AbstractProblemDetector (): void 100% (1/1)100% (8/8)100% (2/2)
getFieldNameRange (IApiField, IDocument, IReference): Position 100% (1/1)100% (10/10)100% (1/1)
getRetainedReferences (): List 100% (1/1)100% (3/3)100% (1/1)
getTypeName (IApiMember): String 100% (1/1)100% (30/30)100% (8/8)
retainReference (IReference): void 100% (1/1)100% (6/6)100% (2/2)

1/*******************************************************************************
2 * Copyright (c) 2008, 2009 IBM Corporation and others.
3 * All rights reserved. This program and the accompanying materials
4 * are made available under the terms of the Eclipse Public License v1.0
5 * which accompanies this distribution, and is available at
6 * http://www.eclipse.org/legal/epl-v10.html
7 *
8 * Contributors:
9 *     IBM Corporation - initial API and implementation
10 *******************************************************************************/
11package org.eclipse.pde.api.tools.internal.builder;
12 
13import java.util.Iterator;
14import java.util.LinkedList;
15import java.util.List;
16 
17import org.eclipse.core.resources.IProject;
18import org.eclipse.core.resources.IResource;
19import org.eclipse.core.runtime.CoreException;
20import org.eclipse.core.runtime.NullProgressMonitor;
21import org.eclipse.jdt.core.Flags;
22import org.eclipse.jdt.core.ICompilationUnit;
23import org.eclipse.jdt.core.IField;
24import org.eclipse.jdt.core.IJavaElement;
25import org.eclipse.jdt.core.IJavaProject;
26import org.eclipse.jdt.core.IMethod;
27import org.eclipse.jdt.core.ISourceRange;
28import org.eclipse.jdt.core.IType;
29import org.eclipse.jdt.core.JavaModelException;
30import org.eclipse.jdt.core.Signature;
31import org.eclipse.jface.text.BadLocationException;
32import org.eclipse.jface.text.IDocument;
33import org.eclipse.jface.text.Position;
34import org.eclipse.pde.api.tools.internal.model.PluginProjectApiComponent;
35import org.eclipse.pde.api.tools.internal.problems.ApiProblemFactory;
36import org.eclipse.pde.api.tools.internal.provisional.ApiPlugin;
37import org.eclipse.pde.api.tools.internal.provisional.IApiMarkerConstants;
38import org.eclipse.pde.api.tools.internal.provisional.builder.IApiProblemDetector;
39import org.eclipse.pde.api.tools.internal.provisional.builder.IReference;
40import org.eclipse.pde.api.tools.internal.provisional.model.IApiComponent;
41import org.eclipse.pde.api.tools.internal.provisional.model.IApiElement;
42import org.eclipse.pde.api.tools.internal.provisional.model.IApiField;
43import org.eclipse.pde.api.tools.internal.provisional.model.IApiMember;
44import org.eclipse.pde.api.tools.internal.provisional.model.IApiMethod;
45import org.eclipse.pde.api.tools.internal.provisional.model.IApiType;
46import org.eclipse.pde.api.tools.internal.provisional.problems.IApiProblem;
47import org.eclipse.pde.api.tools.internal.util.Signatures;
48import org.eclipse.pde.api.tools.internal.util.Util;
49 
50/**
51 * @since 1.1
52 */
53public abstract class AbstractProblemDetector implements IApiProblemDetector {
54 
55        /**
56         * Constant used for controlling tracing in the problem detectors
57         */
58        protected static boolean DEBUG = Util.DEBUG;
59        
60        /**
61         * Method used for initializing tracing in the problem detectors
62         */
63        public static void setDebug(boolean debugValue) {
64                DEBUG = debugValue || Util.DEBUG;
65        }
66        
67        /**
68         * List of potential {@link IReference} problems
69         */
70        private List fPotentialProblems = new LinkedList();
71        
72        /**
73         * Retains the reference for further analysis.
74         *  
75         * @param reference reference
76         */
77        protected void retainReference(IReference reference) {
78                fPotentialProblems.add(reference);
79        }
80 
81        /**
82         * Return the list of retained references.
83         * 
84         * @return references
85         */
86        protected List getRetainedReferences() {
87                return fPotentialProblems;
88        }
89        
90        /**
91         * Creates a problem for a specific reference in the workspace
92         * 
93         * @param reference reference
94         * @param associated java project (with reference source location)
95         * @return problem or <code>null</code> if none
96         * @exception CoreException if something goes wrong
97         */
98        protected IApiProblem createProblem(IReference reference, IJavaProject javaProject) {
99                IProject project = javaProject.getProject();
100                if (ApiPlugin.getDefault().getSeverityLevel(getSeverityKey(), project) == ApiPlugin.SEVERITY_IGNORE) {
101                        return null;
102                }                
103                try {
104                        String lookupName = getTypeName(reference.getMember()).replace('$', '.');
105                        IType type = javaProject.findType(lookupName, new NullProgressMonitor());
106                        if (type == null) {
107                                return null;
108                        }
109                        ICompilationUnit compilationUnit = type.getCompilationUnit();
110                        if (compilationUnit == null) {
111                                return null;
112                        }
113                        IResource resource = Util.getResource(project, type);
114                        if (resource == null) {
115                                return null;
116                        }
117                        int charStart = -1;
118                        int charEnd = -1;
119                        int lineNumber = reference.getLineNumber();
120                        IJavaElement element = compilationUnit;
121                        if (!Util.isManifest(resource.getProjectRelativePath()) && !type.isBinary()) {
122                                IDocument document = Util.getDocument(compilationUnit);
123                                // retrieve line number, char start and char end
124                                if (lineNumber > 0) {
125                                        lineNumber--;
126                                }
127                                // get the source range for the problem
128                                try {
129                                        Position pos = getSourceRange(type, document, reference);
130                                        if (pos != null) {
131                                                charStart = pos.getOffset();
132                                                if (charStart != -1) {
133                                                        charEnd = charStart + pos.getLength();
134                                                        lineNumber = document.getLineOfOffset(charStart);
135                                                }
136                                        }
137                                } catch (CoreException e) {
138                                        ApiPlugin.log(e);
139                                        return null;
140                                }
141                                catch (BadLocationException e) {
142                                        ApiPlugin.log(e);
143                                        return null;
144                                }
145                                if(charStart > -1) {
146                                        element = compilationUnit.getElementAt(charStart);
147                                }
148                        }
149                        return ApiProblemFactory.newApiUsageProblem(resource.getProjectRelativePath().toPortableString(),
150                                        type.getFullyQualifiedName(),
151                                        getMessageArgs(reference), 
152                                        new String[] {IApiMarkerConstants.MARKER_ATTR_HANDLE_ID, IApiMarkerConstants.API_MARKER_ATTR_ID}, 
153                                        new Object[] {(element == null ? compilationUnit.getHandleIdentifier() : element.getHandleIdentifier()),
154                                                                   new Integer(IApiMarkerConstants.API_USAGE_MARKER_ID)}, 
155                                        lineNumber, 
156                                        charStart, 
157                                        charEnd, 
158                                        getElementType(reference), 
159                                        getProblemKind(),
160                                        getProblemFlags(reference));
161                } catch (CoreException e) {
162                        ApiPlugin.log(e);
163                }
164                return null;
165        }
166        
167        /**
168         * Returns the source range to include in the associated problem or <code>null</code>
169         * if a valid source range could not be computed.
170         * 
171         * @param type resolved type where the reference occurs
172         * @param doc source document of the type
173         * @param reference associated reference
174         * @return source range as a position
175         */
176        protected abstract Position getSourceRange(IType type, IDocument doc, IReference reference) throws CoreException, BadLocationException;
177 
178        /**
179         * Returns the element type the problem is reported on.
180         * 
181         * @return
182         */
183        protected abstract int getElementType(IReference reference);
184        
185        /**
186         * Returns problem flags, if any.
187         * 
188         * @param reference
189         * @return problem flags
190         */
191        protected abstract int getProblemFlags(IReference reference);
192        
193        /**
194         * Returns problem message arguments
195         * 
196         * @return message arguments
197         */
198        protected abstract String[] getMessageArgs(IReference reference) throws CoreException;
199        
200        /**
201         * Returns problem message arguments to be used in headless build
202         * 
203         * @return message arguments
204         */        
205        protected abstract String[] getQualifiedMessageArgs(IReference reference) throws CoreException;
206        
207        /**
208         * Returns the kind of problem to create
209         * 
210         * @return problem kind
211         */
212        protected abstract int getProblemKind();
213        
214        /**
215         * Returns the key used to lookup problem severity.
216         * 
217         * @return problem severity key
218         */
219        protected abstract String getSeverityKey();
220        
221        /**
222         * Returns the fully qualified type name associated with the given member.
223         * 
224         * @param member
225         * @return fully qualified type name
226         */
227        protected String getTypeName(IApiMember member) throws CoreException {
228                switch (member.getType()) {
229                        case IApiElement.TYPE: {
230                                IApiType type = (IApiType) member;
231                                if(type.isAnonymous()) {
232                                        return getTypeName(member.getEnclosingType());
233                                }
234                                else if(type.isLocal()) {
235                                        return getTypeName(member.getEnclosingType());
236                                }
237                                return member.getName();
238                        }
239                        default: {
240                                return getTypeName(member.getEnclosingType());
241                        }
242                }
243        }
244        
245        /**
246         * Returns the qualified type name to display. This method delegates to the 
247         * {@link Signatures} class to build the display signatures
248         * @param member
249         * @return fully qualified display signature for the given {@link IApiType} or enclosing
250         * type if the member is not a type itself
251         * @throws CoreException
252         */
253        protected String getQualifiedTypeName(IApiMember member) throws CoreException {
254                switch (member.getType()) {
255                        case IApiElement.TYPE: {
256                                IApiType type = (IApiType) member;
257                                if(type.isAnonymous()) {
258                                        return getQualifiedTypeName(member.getEnclosingType());
259                                }
260                                else if(type.isLocal()) {
261                                        String name = getTypeName(member.getEnclosingType());
262                                        int idx = name.indexOf('$');
263                                        if(idx > -1) {
264                                                return name.substring(0, idx);
265                                        }
266                                        return name;
267                                }
268                                return Signatures.getQualifiedTypeSignature((IApiType) member);
269                        }
270                        default: {
271                                return getQualifiedTypeName(member.getEnclosingType());
272                        }
273                }
274        }
275        
276        /**
277         * Returns the unqualified type name associated with the given member.
278         * 
279         * @param member
280         * @return unqualified type name
281         */
282        protected String getSimpleTypeName(IApiMember member) throws CoreException {
283                switch (member.getType()) {
284                        case IApiElement.TYPE: {
285                                IApiType type = (IApiType) member;
286                                if(type.isAnonymous()) {
287                                        return getSimpleTypeName(type.getEnclosingType());
288                                }
289                                else if(type.isLocal()) {
290                                        String name = getSimpleTypeName(member.getEnclosingType());
291                                        int idx = name.indexOf('$');
292                                        if(idx > -1) {
293                                                return name.substring(0, idx);
294                                        }
295                                        return name;
296                                }
297                                return Signatures.getTypeName(Signatures.getTypeSignature(type));
298                        }
299                        default:
300                                return getSimpleTypeName(member.getEnclosingType());
301                }
302        }        
303        
304        /**
305         * Default strategy for when no source position can be computed: creates
306         * a {@link Position} for the name of the given {@link IType}. Returns <code>null</code> in the event
307         * the given {@link IType} is <code>null</code> or the name range cannot be computed for the type.
308         * 
309         * @param type the type
310         * @param reference the reference
311         * @throws CoreException
312         * @return returns a default {@link Position} for the name range of the given {@link IType}
313         */
314        protected Position defaultSourcePosition(IType type, IReference reference) throws CoreException {
315                if(type != null) {
316                        ISourceRange range = type.getNameRange();
317                        if(range != null) {
318                                return new Position(range.getOffset(), range.getLength());
319                        }
320                }
321                return null;
322        }
323        
324        /**
325         * Finds the method name to select on the given line of code starting from the given index.
326         * This method will recurse to find a method name in the even there is a name clash with the type.
327         * For example:
328         * <pre>
329         *                 MyType type = new MyType();
330         * </pre>
331         * If we are trying to find the constructor method call we have a name collision (and the first occurrence of MyType would be selected). 
332         * <br>
333         * A name is determined to be a method name if it is followed by a '(' character (excluding spaces)
334         * @param namepart
335         * @param line
336         * @param index
337         * @return the index of the method name on the given line or -1 if not found
338         */
339        protected int findMethodNameStart(String namepart, String line, int index) {
340                int start = line.indexOf(namepart, index);
341                if(start < 0) {
342                        return -1;
343                }
344                int offset = start+namepart.length();
345                while(line.charAt(offset) == ' ') {
346                        offset++;
347                }
348                if(line.charAt(offset) == '(' ||
349                                line.charAt(offset) == '<') {
350                        return start;
351                }
352                return findMethodNameStart(namepart, line, offset);
353        }        
354        
355        /* (non-Javadoc)
356         * @see org.eclipse.pde.api.tools.internal.provisional.search.IApiProblemDetector#createProblems()
357         */
358        public List createProblems() {
359                List references = getRetainedReferences();
360                List problems = new LinkedList();
361                Iterator iterator = references.iterator();
362                while (iterator.hasNext()) {
363                        IReference reference = (IReference) iterator.next();
364                        if (reference.getResolvedReference() == null) {
365                                // TODO: unresolved reference
366                        } else {
367                                if (isProblem(reference)) {
368                                        try {
369                                                IApiProblem problem = null;
370                                                IApiComponent component = reference.getMember().getApiComponent();
371                                                if (component instanceof PluginProjectApiComponent) {
372                                                        PluginProjectApiComponent ppac = (PluginProjectApiComponent) component;
373                                                        IJavaProject project = ppac.getJavaProject();
374                                                        problem = createProblem(reference, project);
375                                                } else {
376                                                        problem = createProblem(reference);
377                                                }
378                                                if (problem != null) {
379                                                        problems.add(problem);
380                                                }
381                                        } catch (CoreException e) {
382                                                ApiPlugin.log(e.getStatus());
383                                        }
384                                }
385                        }
386                }
387                return problems;
388        }
389 
390        /**
391         * Returns whether the resolved reference is a real problem.
392         * 
393         * @param reference
394         * @return whether a problem
395         */
396        protected boolean isProblem(IReference reference) {
397                //by default fragment -> host references are not problems 
398                //https://bugs.eclipse.org/bugs/show_bug.cgi?id=255659
399                IApiMember member = reference.getResolvedReference();
400                if(member != null) {
401                        IApiMember local = reference.getMember();
402                        try {
403                                IApiComponent lcomp = local.getApiComponent();
404                                if(lcomp != null && lcomp.isFragment()) {
405                                        return !lcomp.getHost().equals(member.getApiComponent());
406                                }
407                        }
408                        catch(CoreException ce) {
409                                ApiPlugin.log(ce);
410                        }
411                }
412                return true;
413        }
414        
415        /**
416         * Tries to find the given {@link IApiMethod} in the given {@link IType}. If a matching method is not
417         * found <code>null</code> is returned 
418         * @param type the type top look in for the given {@link IApiMethod}
419         * @param method the {@link IApiMethod} to look for
420         * @return the {@link IMethod} from the given {@link IType} that matches the given {@link IApiMethod} or <code>null</code> if no
421         * matching method is found
422         * @throws JavaModelException
423         * @throws CoreException
424         */
425        protected IMethod findMethodInType(IType type, IApiMethod method) throws JavaModelException, CoreException {
426                String[] parameterTypes = Signature.getParameterTypes(method.getSignature());
427                for (int i = 0; i < parameterTypes.length; i++) {
428                        parameterTypes[i] = parameterTypes[i].replace('/', '.');
429                }
430                String methodname = method.getName();
431                if(method.isConstructor()) {
432                        IApiType enclosingType = method.getEnclosingType();
433                        if (enclosingType.isMemberType() && !Flags.isStatic(enclosingType.getModifiers())) {
434                                // remove the synthetic argument that corresponds to the enclosing type
435                                int length = parameterTypes.length - 1;
436                                System.arraycopy(parameterTypes, 1, (parameterTypes = new String[length]), 0, length);
437                        }
438                        methodname = enclosingType.getSimpleName();
439                }
440                IMethod Qmethod = type.getMethod(methodname, parameterTypes);
441                IMethod[] methods = type.getMethods();
442                IMethod match = null;
443                for (int i = 0; i < methods.length; i++) {
444                        IMethod m = methods[i];
445                        if (m.isSimilar(Qmethod)) {
446                                match = m;
447                                break;
448                        }
449                }
450                return match;
451        }
452        
453        /**
454         * Returns the source range for the given {@link IApiMethod} within the given {@link IType}
455         * @param type the type to look for the method within
456         * @param reference the reference the method comes from
457         * @param method the {@link IApiMethod} to look for the source range for
458         * @return the {@link ISourceRange} in the {@link IType} enclosing the given {@link IApiMethod}
459         * @throws CoreException
460         * @throws JavaModelException
461         */
462        protected Position getSourceRangeForMethod(IType type, IReference reference, IApiMethod method) throws CoreException, JavaModelException {
463                IMethod match = findMethodInType(type, method);
464                Position pos = null;
465                if (match != null) {
466                        ISourceRange range = match.getNameRange();
467                        if(range != null) {
468                                pos = new Position(range.getOffset(), range.getLength());
469                        }
470                }
471                if(pos == null) {
472                        return defaultSourcePosition(type, reference);
473                }
474                return pos;
475        }
476        
477        /**
478         * Returns the source range to use for the given field within the given {@link IType}
479         * @param type the type to look in for the given {@link IApiField}
480         * @param reference the reference the field is involved in
481         * @param field the field to find the range for
482         * @return the {@link ISourceRange} in the given {@link IType} that encloses the given {@link IApiField} 
483         * @throws JavaModelException
484         * @throws CoreException
485         */
486        protected Position getSourceRangeForField(IType type, IReference reference, IApiField field) throws JavaModelException, CoreException {
487                IField javaField = type.getField(field.getName());
488                Position pos = null;
489                if (javaField.exists()) {
490                        ISourceRange range = javaField.getNameRange();
491                        if(range != null) {
492                                pos = new Position(range.getOffset(), range.getLength()); 
493                        }
494                }
495                if(pos == null) {
496                        return defaultSourcePosition(type, reference);
497                }
498                return pos;
499        }
500        
501        /**
502         * Returns the range of the name of the given {@link IApiField} to select when creating {@link IApiProblem}s.
503         * Source ranges are computed and tried in the following order:
504         * <ol>
505         * <li>Try the type-qualified name of the variable</li>
506         * <li>Try looking for 'super.variable'</li>
507         * <li>Try looking for 'this.variable'</li>
508         * <li>Try looking for pattern '*.variable'</li>
509         * <li>Else select the entire line optimistically</li>
510         * </ol>
511         * @param field the field to find the name range for
512         * @param document the document to look within
513         * @param reference the reference the field is from
514         * @return the range of text to select, or <code>null</code> if one could not be computed
515         * @throws BadLocationException
516         * @throws CoreException
517         */
518        protected Position getFieldNameRange(IApiField field, IDocument document, IReference reference) throws BadLocationException, CoreException {
519                return getFieldNameRange(field.getEnclosingType().getName(), field.getName(), document, reference);
520        }
521        protected Position getFieldNameRange(String typeName, String fieldName, IDocument document, IReference reference) throws BadLocationException, CoreException {
522                int linenumber = reference.getLineNumber();
523                if (linenumber > 0) {
524                        linenumber--;
525                }
526                if (linenumber > 0) {
527                        int offset = document.getLineOffset(linenumber);
528                        String line = document.get(offset, document.getLineLength(linenumber));
529                        String qname = typeName +"."+fieldName; //$NON-NLS-1$
530                        int first = line.indexOf(qname);
531                        if(first < 0) {
532                                qname = "super."+fieldName; //$NON-NLS-1$
533                                first = line.indexOf(qname);
534                        }
535                        if(first < 0) {
536                                qname = "this."+fieldName; //$NON-NLS-1$
537                                first = line.indexOf(qname);
538                        }
539                        if(first < 0) {
540                                //try a pattern [.*fieldname] 
541                                //the field might be ref'd via a constant, e.g. enum constant
542                                int idx = line.indexOf(fieldName);
543                                while(idx > -1) {
544                                        if(line.charAt(idx-1) == '.') {
545                                                first = idx;
546                                                qname = fieldName;
547                                                break;
548                                        }
549                                        idx = line.indexOf(fieldName, idx+1);
550                                }
551                        }
552                        Position pos = null;
553                        if(first > -1) {
554                                pos = new Position(offset + first, qname.length());
555                        }
556                        else {
557                                //optimistically select the whole line since we can't find the correct variable name and we can't just select
558                                //the first occurrence
559                                pos = new Position(offset, line.length());
560                        }
561                        return pos;
562                }
563                return null;
564        }
565        
566        /**
567         * Searches for the name of a method at the line number specified in the given
568         * reference.
569         * 
570         * @param name method name
571         * @param document document to search in
572         * @param reference provides line number
573         * @return method name range
574         * @throws CoreException
575         */
576        protected Position getMethodNameRange(boolean isContructor, String name, IDocument document, IReference reference) throws CoreException, BadLocationException {
577                int linenumber = reference.getLineNumber();
578                if (linenumber > 0) {
579                        linenumber--;
580                }
581                String methodname = name;
582                int idx = methodname.indexOf('$');
583                if(idx > -1) {
584                        methodname = methodname.substring(0, idx);
585                }
586                idx = methodname.indexOf(Signatures.getLT());
587                if(idx > -1) {
588                        methodname = methodname.substring(0, idx);
589                }
590                int offset = document.getLineOffset(linenumber);
591                String line = document.get(offset, document.getLineLength(linenumber));
592                int start = line.indexOf('=');
593                if(start < 0) {
594                        if (isContructor) {
595                                // new keyword should only be checked if the method is a constructor
596                                start = line.indexOf("new"); //$NON-NLS-1$
597                                if(start < 0) {
598                                        start = 0;
599                                }
600                        } else {
601                                start = 0;
602                        }
603                }
604                else {
605                        char charat = line.charAt(start-1);
606                        //make sure its not '==' | '!=' | '<=' | '>='
607                        if(line.charAt(start+1) == '=' ||
608                                        charat == '!' || charat == '<' || charat == '>') {
609                                start = 0;
610                        }
611                }
612                int first = findMethodNameStart(methodname, line, start);
613                if(first < 0) {
614                        methodname = "super"; //$NON-NLS-1$
615                        first = findMethodNameStart(methodname, line, start);
616                }
617                if(first > -1) {
618                        return new Position(offset + first, methodname.length());
619                }
620                return null;
621        }
622        /* (non-Javadoc)
623         * @see org.eclipse.pde.api.tools.internal.search.AbstractProblemDetector#createProblem(org.eclipse.pde.api.tools.internal.provisional.model.IReference)
624         */
625        protected IApiProblem createProblem(IReference reference) throws CoreException {
626                int lineNumber = reference.getLineNumber();
627                if (lineNumber > 0) {
628                        lineNumber--;
629                }
630                String ltypename = getTypeName(reference.getMember());
631                return ApiProblemFactory.newApiUsageProblem(
632                                null,
633                                ltypename,
634                                getQualifiedMessageArgs(reference),
635                                new String[] {IApiMarkerConstants.API_MARKER_ATTR_ID}, 
636                                new Object[] {new Integer(IApiMarkerConstants.API_USAGE_MARKER_ID)}, 
637                                lineNumber, 
638                                IApiProblem.NO_CHARRANGE, 
639                                IApiProblem.NO_CHARRANGE,
640                                getElementType(reference), 
641                                getProblemKind(),
642                                getProblemFlags(reference));
643        }        
644        
645}

[all classes][org.eclipse.pde.api.tools.internal.builder]
EMMA 2.0.5312 EclEmma Fix 1 (C) Vladimir Roubtsov