Clover coverage report - XJavaDoc - 1.1 Coverage timestamp: Sun Oct 3 2004 19:56:54 BST FRAMES NO FRAMES |
file stats: | LOC: | 775 |  | Methods: | 35
| NCLOC: | 492 |  | Classes: | 1
30 day Evaluation Version distributed via the Maven Jar Repository. Clover is not free. You have 30 days to evaluate it. Please visit http://www.thecortex.net/clover to obtain a licensed version of Clover
Source file | Conditionals | Statements | Methods | TOTAL
SourceClass.java | 47.2% | 62.4% | 71.4% | 58.6% |

1 |  |
     /*
2 |  |
      * Copyright (c) 2001-2003 The XDoclet team
3 |  |
      * All rights reserved.
4 |  |
      */
5 |  |
     package xjavadoc;
6 |  |
7 |  |
     import xjavadoc.filesystem.AbstractFile;
8 |  |
     import xjavadoc.filesystem.XJavadocFile;
9 |  |
     import xjavadoc.filesystem.ReaderFile;
10 |  |
11 |  |
     import java.util.*;
12 |  |
     import java.io.*;
13 |  |
14 |  |
     /**
15 |  |
      * This class represents a class for which the source code is available
16 |  |
      *XJavaDocFil
17 |  |
      * @author    Aslak Hellesøy
18 |  |
      * @created   3. januar 2002
19 |  |
      */
20 |  |
     public final class SourceClass extends AbstractClass
21 |  |
     {
22 |  |
         public static int  instanceCount = 0;
23 |  |
24 |  |
         private final Map  _qualifiedClasses = new HashMap();
25 |  |
26 |  |
         private final boolean _isExtraClass;
27 |  |
28 |  |
         private final List _tagsForValidation = new ArrayList();
29 |  |
30 |  |
         /**
31 |  |
          * The root node of the AST
32 |  |
          */
33 |  |
         private SimpleNode _compilationUnit;
34 |  |
35 |  |
         private Reader     _in = null;
36 |  |
37 |  |
         /**
38 |  |
          * Keep a ref to the file in case of warning reporting
39 |  |
          */
40 |  |
         private AbstractFile _sourceFile;
41 |  |
42 |  |
         //private JavaParser _parser;
43 |  |
44 |  |
         /**
45 |  |
          * doe we nees saving?
46 |  |
          */
47 |  |
         private boolean    _dirty;
48 |  |
49 |  |
         /**
50 |  |
          * Constructor to use for inner classes.
51 |  |
          *
52 |  |
          * @param containingClass  The containing class;
53 |  |
          */
54 | 252 |
         public SourceClass( SourceClass containingClass, XTagFactory tagFactory )
55 |  |
         {
56 | 252 |
             super( containingClass, tagFactory );
57 | 252 |
             setContainingPackage( containingClass.getContainingPackage().getName() );
58 | 252 |
             _isExtraClass = false;
59 |  |
         }
60 |  |
61 |  |
         /**
62 |  |
          * Constructor to use for "extra" classes, that is, secondary classes that
63 |  |
          * figure in the same source.
64 |  |
          *
65 |  |
          * @param mainClass  The containing class. Or rather the "main" class in the
66 |  |
          *      source.
67 |  |
          * @param dummy
68 |  |
          */
69 | 48 |
         public SourceClass( SourceClass mainClass, int dummy, XTagFactory tagFactory )
70 |  |
         {
71 | 48 |
             super( mainClass.getXJavaDoc(), tagFactory );
72 | 48 |
             setContainingPackage( mainClass.getContainingPackage().getName() );
73 | 48 |
             _isExtraClass = true;
74 | 48 |
             _sourceFile = mainClass.getFile();
75 |  |
         }
76 |  |
77 |  |
         /**
78 |  |
          * Constructor to use for outer classes
79 |  |
          *
80 |  |
          * @param sourceFile  The file containing the source
81 |  |
          */
82 | 0 |
         public SourceClass( XJavaDoc xJavaDoc, File sourceFile, XTagFactory tagFactory )
83 |  |
         {
84 | 0 |
             this( xJavaDoc, new XJavadocFile( sourceFile ), false, tagFactory, null );
85 |  |
         }
86 |  |
87 |  |
         /**
88 |  |
          * Constructor to use for outer classes
89 |  |
          *
90 |  |
          * @param sourceFile  The file containing the source
91 |  |
          */
92 | 0 |
         public SourceClass( XJavaDoc xJavaDoc, Reader sourceFile, XTagFactory tagFactory )
93 |  |
         {
94 | 0 |
             this( xJavaDoc, new ReaderFile( sourceFile ), false, tagFactory, null);
95 |  |
         }
96 |  |
97 |  |
         /**
98 |  |
          * @param sourceFile
99 |  |
          * @param useNodeParser
100 |  |
          */
101 | 12 |
         public SourceClass( XJavaDoc xJavaDoc, File sourceFile, boolean useNodeParser, XTagFactory tagFactory )
102 |  |
         {
103 | 12 |
             this( xJavaDoc, new XJavadocFile( sourceFile ), useNodeParser, tagFactory ,null );
104 |  |
         }
105 |  |
106 |  |
         /**
107 |  |
          * Constructor to use for outer classes
108 |  |
          *
109 |  |
          * @param sourceFile     The file containing the source
110 |  |
          * @param useNodeParser
111 |  |
          */
112 | 684 |
         public SourceClass( XJavaDoc xJavaDoc, AbstractFile sourceFile, boolean useNodeParser, XTagFactory tagFactory ,String encoding)
113 |  |
         {
114 | 684 |
             super( xJavaDoc, tagFactory );
115 | 684 |
             if( sourceFile == null )
116 |  |
             {
117 | 0 |
                 throw new IllegalArgumentException( "sourceFile can't be null for outer classes!" );
118 |  |
             }
119 | 684 |
             _sourceFile = sourceFile;
120 |  |
121 | 684 |
             try
122 |  |
             {
123 | 684 |
                 _in = sourceFile.getReader(encoding);
124 | 684 |
                 parse( useNodeParser );
125 |  |
             }
126 |  |
             catch( IOException e )
127 |  |
             {
128 |  |
                 // That's tough. Shouldn't happen
129 | 0 |
                 if(encoding==null)
130 |  |
                 {
131 | 0 |
                 throw new IllegalStateException( "Couldn't find " + sourceFile );
132 |  |
             }
133 |  |
                 else
134 |  |
                 {
135 | 0 |
                     throw new IllegalStateException( "Invalid Encoding '"+encoding+"' or couldn't find '" + sourceFile +"'");
136 |  |
                 }
137 |  |
             }
138 |  |
139 | 684 |
             instanceCount++;
140 | 684 |
             _dirty = false;
141 | 684 |
             _isExtraClass = false;
142 |  |
         }
143 |  |
144 |  |
         /**
145 |  |
          * Describe what the method does
146 |  |
          *
147 |  |
          * @param qualifiedName  Describe what the parameter does
148 |  |
          * @return               Describe the return value
149 |  |
          */
150 | 8 |
         public static String getFileName( String qualifiedName )
151 |  |
         {
152 | 8 |
             return qualifiedName.replace( '.', File.separatorChar ) + ".java";
153 |  |
         }
154 |  |
155 | 1386 |
         public boolean isExtraClass()
156 |  |
         {
157 | 1386 |
             return _isExtraClass;
158 |  |
         }
159 |  |
160 |  |
         /**
161 |  |
          * Returns "1", "2", etc., depending on how many inner classes we have.
162 |  |
          *
163 |  |
          * @return String containing number of next anonymous inner class
164 |  |
          */
165 | 40 |
         public String getNextAnonymousClassName()
166 |  |
         {
167 | 40 |
             return String.valueOf( getInnerClasses().size() + 1 );
168 |  |
         }
169 |  |
170 |  |
         /**
171 |  |
          * Gets the OuterClass attribute of the SourceClass object
172 |  |
          *
173 |  |
          * @return   The OuterClass value
174 |  |
          */
175 | 4 |
         private boolean isOuterClass()
176 |  |
         {
177 | 4 |
             return _sourceFile != null;
178 |  |
         }
179 |  |
180 |  |
         /**
181 |  |
          * Gets the Writeable attribute of the SourceClass object
182 |  |
          *
183 |  |
          * @return   The Writeable value
184 |  |
          */
185 | 16 |
         public boolean isWriteable()
186 |  |
         {
187 | 16 |
             return _compilationUnit != null;
188 |  |
         }
189 |  |
190 | 4 |
         public SimpleNode getCompilationUnit()
191 |  |
         {
192 | 4 |
             return _compilationUnit;
193 |  |
         }
194 |  |
195 |  |
         /**
196 |  |
          * Returns a reader for the source code.
197 |  |
          *
198 |  |
          * @return   a reader for the source code.
199 |  |
          */
200 | 684 |
         public Reader getReader()
201 |  |
         {
202 | 684 |
             return _in;
203 |  |
         }
204 |  |
205 | 48 |
         public AbstractFile getFile()
206 |  |
         {
207 | 48 |
             return _sourceFile;
208 |  |
         }
209 |  |
210 | 0 |
         public boolean isPrimitive()
211 |  |
         {
212 | 0 |
             return false;
213 |  |
         }
214 |  |
215 |  |
         /**
216 |  |
          * say this class is dirty and needs saving propagate to outer class ( if any )
217 |  |
          */
218 | 0 |
         public void setDirty()
219 |  |
         {
220 | 0 |
             if( isInner() )
221 |  |
             {
222 | 0 |
                 getContainingClass().setDirty();
223 |  |
             }
224 |  |
             else
225 |  |
             {
226 | 0 |
                 _dirty = true;
227 |  |
             }
228 |  |
         }
229 |  |
         /**
230 |  |
          * Called by JavaParser at the end of the parsing
231 |  |
          *
232 |  |
          * @param compilationUnit  The new CompilationUnit value
233 |  |
          */
234 | 12 |
         public void setCompilationUnit( SimpleNode compilationUnit )
235 |  |
         {
236 | 12 |
             _compilationUnit = compilationUnit;
237 |  |
         }
238 |  |
239 |  |
         /**
240 |  |
          * Called by XJavaDoc after the entire source is parsed, but only if validation
241 |  |
          * is on.
242 |  |
          *
243 |  |
          * @throws TagValidationException
244 |  |
          */
245 | 0 |
         public void validateTags() throws TagValidationException
246 |  |
         {
247 |  |
             // Validate the tags on the class level and on our members.
248 | 0 |
             for( Iterator i = _tagsForValidation.iterator(); i.hasNext();  )
249 |  |
             {
250 | 0 |
                 XTag tag = ( XTag ) i.next();
251 |  |
252 | 0 |
                 tag.validate();
253 |  |
             }
254 |  |
255 |  |
             // then validate tags in all our inner classes.
256 | 0 |
             for( Iterator i = getInnerClasses().iterator(); i.hasNext();  )
257 |  |
             {
258 | 0 |
                 SourceClass inner = ( SourceClass ) i.next();
259 |  |
260 | 0 |
                 inner.validateTags();
261 |  |
             }
262 |  |
         }
263 |  |
264 | 710 |
         public void addTagForValidation( DefaultXTag tag )
265 |  |
         {
266 | 710 |
             _tagsForValidation.add( tag );
267 |  |
         }
268 |  |
269 | 0 |
         public boolean saveNeeded()
270 |  |
         {
271 | 0 |
             return isWriteable() && _dirty;
272 |  |
         }
273 |  |
274 |  |
         /**
275 |  |
          * Describe what the method does
276 |  |
          *
277 |  |
          * @return   Describe the return value
278 |  |
          */
279 | 4 |
         public long lastModified()
280 |  |
         {
281 | 4 |
             if( isOuterClass() )
282 |  |
             {
283 | 4 |
                 return _sourceFile.lastModified();
284 |  |
             }
285 |  |
             else
286 |  |
             {
287 | 0 |
                 return getContainingClass().lastModified();
288 |  |
             }
289 |  |
         }
290 |  |
291 |  |
         /**
292 |  |
          * Prints this class to a stream
293 |  |
          *
294 |  |
          * @param out  Describe what the parameter does
295 |  |
          */
296 | 8 |
         public void print( Writer out )
297 |  |
         {
298 | 8 |
             updateDoc();
299 | 8 |
             if( !isWriteable() )
300 |  |
             {
301 |  |
                 // parsed with simple parser
302 | 0 |
                 throw new UnsupportedOperationException( "Can't save classes that are parsed with simpleparser" );
303 |  |
             }
304 | 8 |
             NodePrinter.print( _compilationUnit, out );
305 |  |
         }
306 |  |
307 |  |
         /**
308 |  |
          * Saves the class at root dir rootDir. The actual java file is derived from
309 |  |
          * tha package name. If no root dir is specified, save where it was loaded from
310 |  |
          *
311 |  |
          * @param rootDir       the root directory.
312 |  |
          * @return              the relative fileName to which the file was saved.
313 |  |
          * @throws IOException  if the file couldn't be saved
314 |  |
          */
315 | 8 |
         public String save( File rootDir ) throws IOException
316 |  |
         {
317 | 8 |
             if( !isWriteable() )
318 |  |
             {
319 | 0 |
                 throw new UnsupportedOperationException( "Can't save classes that aren't parsed in AST mode (do getXJavaDoc().setUseNodeParser(true) before parsing starts!)" );
320 |  |
             }
321 | 8 |
             if( getContainingClass() != null )
322 |  |
             {
323 |  |
                 // inner class. can't save these.
324 | 0 |
                 throw new UnsupportedOperationException( "Can't save inner classes" );
325 |  |
             }
326 | 8 |
             else if( rootDir != null )
327 |  |
             {
328 | 8 |
                 String fileName = getFileName( getQualifiedName() );
329 | 8 |
                 File javaFile = new File( rootDir, fileName );
330 |  |
331 | 8 |
                 javaFile.getParentFile().mkdirs();
332 | 8 |
                 FileWriter fwtr = new FileWriter( javaFile );
333 | 8 |
                 print( fwtr );
334 | 8 |
                 fwtr.flush();
335 | 8 |
                 fwtr.close();
336 | 8 |
                 return fileName;
337 |  |
             }
338 |  |
             else
339 |  |
             {
340 |  |
                 // no root dir specified, save in place
341 | 0 |
                 Writer outputStream = _sourceFile.getWriter();
342 |  |
343 | 0 |
                 print( new PrintWriter( outputStream ) );
344 | 0 |
                 outputStream.flush();
345 | 0 |
                 outputStream.close();
346 | 0 |
                 return _sourceFile.toString();
347 |  |
             }
348 |  |
         }
349 |  |
350 |  |
         /**
351 |  |
          * Returns fully qualified name of a class. 1: check for "." 2: if "." it's
352 |  |
          * already qualified 3: if no ".", must try with all imported packages or
353 |  |
          * classes
354 |  |
          *
355 |  |
          * @param unqualifiedClassName  Describe what the parameter does
356 |  |
          * @return                      Describe the return value
357 |  |
          */
358 | 5656 |
         public XClass qualify( final String unqualifiedClassName )
359 |  |
         {
360 | 5656 |
             XClass result = null;
361 |  |
362 | 5656 |
             result = ( XClass ) _qualifiedClasses.get( unqualifiedClassName );
363 | 5656 |
             if( result == null )
364 |  |
             {
365 |  |
366 | 3414 |
                 if( getContainingClass() == null )
367 |  |
                 {
368 |  |
                     // If there are dots, consider it to be qualified or a reference to an inner class in one
369 |  |
                     // of the imported classes.
370 | 3116 |
                     if( unqualifiedClassName.indexOf( '.' ) != -1 )
371 |  |
                     {
372 | 1944 |
                         result = unqualifiedNameInImportedClassesInnerClasses( unqualifiedClassName );
373 | 1944 |
                         if( result == null )
374 |  |
                         {
375 |  |
                             // It wasn't a ref to an imported inner class. Consider it already qualified
376 | 1938 |
                             result = getXJavaDoc().getXClass( unqualifiedClassName );
377 |  |
                         }
378 |  |
                     }
379 |  |
                     else
380 |  |
                     {
381 |  |
                         // There are no dots in the class name. It's a primitive or unqualified.
382 | 1172 |
                         Primitive primitive;
383 |  |
384 | ? |
                         if( ( primitive = XJavaDoc.getPrimitive( unqualifiedClassName ) ) != null )
385 |  |
                         {
386 | 124 |
                             result = primitive;
387 |  |
                         }
388 |  |
                         else
389 |  |
                         {
390 | 1048 |
                             String qualifiedName;
391 |  |
392 | ? |
                             if( ( qualifiedName = unqualifiedNameInTheSameClassAsAnInnerClass( unqualifiedClassName ) ) != null )
393 |  |
                             {
394 | 460 |
                                 result = getXJavaDoc().getXClass( qualifiedName );
395 |  |
                             }
396 | ? |
                             else if( ( qualifiedName = unqualifiedNameInInnerClasses( unqualifiedClassName ) ) != null )
397 |  |
                             {
398 | 46 |
                                 result = getXJavaDoc().getXClass( qualifiedName );
399 |  |
                             }
400 | ? |
                             else if( ( qualifiedName = unqualifiedNameInJavaDotLang( unqualifiedClassName ) ) != null )
401 |  |
                             {
402 | 208 |
                                 result = getXJavaDoc().getXClass( qualifiedName );
403 |  |
                             }
404 | ? |
                             else if( ( qualifiedName = unqualifiedNameInImportedClasses( unqualifiedClassName ) ) != null )
405 |  |
                             {
406 | 212 |
                                 result = getXJavaDoc().getXClass( qualifiedName );
407 |  |
                             }
408 | ? |
                             else if( ( qualifiedName = unqualifiedNameInImportedPackages( unqualifiedClassName ) ) != null )
409 |  |
                             {
410 | 122 |
                                 result = getXJavaDoc().getXClass( qualifiedName );
411 |  |
                             }
412 | 0 |
                             else if( ( qualifiedName = unqualifiedNameInTheSamePackage( unqualifiedClassName ) ) != null )
413 |  |
                             {
414 | 0 |
                                 result = getXJavaDoc().getXClass( qualifiedName );
415 |  |
                             }
416 | 0 |
                             else if( ( qualifiedName = unqualifiedNameInInnerClassesOfSuperClass( unqualifiedClassName ) ) != null )
417 |  |
                             {
418 | 0 |
                                 result = getXJavaDoc().getXClass( qualifiedName );
419 |  |
                             }
420 | 0 |
                             else if( ( qualifiedName = unqualifiedNameInInnerInterface( unqualifiedClassName ) ) != null )
421 |  |
                             {
422 | 0 |
                                 result = getXJavaDoc().getXClass( qualifiedName );
423 |  |
                             }
424 |  |
                             else
425 |  |
                             {
426 | 0 |
                                 String unknownClassName;
427 |  |
428 | 0 |
                                 if( getContainingPackage().getName().equals( "" ) )
429 |  |
                                 {
430 | 0 |
                                     unknownClassName = unqualifiedClassName;
431 |  |
                                 }
432 |  |
                                 else
433 |  |
                                 {
434 | 0 |
                                     unknownClassName = getContainingPackage().getName() + "." + unqualifiedClassName;
435 |  |
                                 }
436 |  |
437 | 0 |
                                 UnknownClass unknownClass = new UnknownClass( getXJavaDoc(), unknownClassName );
438 |  |
439 |  |
                                 /*
440 |  |
                                  * We couldn't qualify the class. If there are no package import statements,
441 |  |
                                  * we'll assume the class belongs to the same package as ourself.
442 |  |
                                  */
443 | 0 |
                                 if( !hasImportedPackages() )
444 |  |
                                 {
445 |  |
                                     // No import foo.bar.* statements. Just add an informative message that we guessed
446 | 0 |
                                     getXJavaDoc().logMessage( this, unknownClass, unqualifiedClassName, XJavaDoc.NO_IMPORTED_PACKAGES );
447 |  |
                                 }
448 |  |
                                 else
449 |  |
                                 {
450 |  |
451 |  |
                                     // We can't decide. Add a warning that will be displayed in the end.
452 | 0 |
                                     getXJavaDoc().logMessage( this, unknownClass, unqualifiedClassName, XJavaDoc.ONE_OR_MORE_IMPORTED_PACKAGES );
453 |  |
                                 }
454 | 0 |
                                 result = unknownClass;
455 |  |
                             }
456 |  |
                         }
457 |  |
                     }
458 |  |
                 }
459 |  |
                 else
460 |  |
                 {
461 | 298 |
                     result = getContainingAbstractClass().qualify( unqualifiedClassName );
462 |  |
                 }
463 | 3414 |
                 _qualifiedClasses.put( unqualifiedClassName, result );
464 |  |
             }
465 |  |
466 | 5656 |
             return result;
467 |  |
         }
468 |  |
469 | 0 |
         public void reset()
470 |  |
         {
471 | 0 |
             super.reset();
472 |  |
473 | 0 |
             _compilationUnit = null;
474 | 0 |
             _in = null;
475 | 0 |
             _sourceFile = null;
476 | 0 |
             _qualifiedClasses.clear();
477 |  |
         }
478 |  |
479 | 334 |
         private final String unqualifiedNameInImportedClasses( final String unqualifiedClassName )
480 |  |
         {
481 | 334 |
             if( !hasImportedClasses() )
482 |  |
             {
483 | 20 |
                 return null;
484 |  |
             }
485 |  |
486 | 314 |
             final String suffix = "." + unqualifiedClassName;
487 | 314 |
             String candidate = null;
488 |  |
489 | 314 |
             for( Iterator i = getImportedClasses().iterator(); i.hasNext();  )
490 |  |
             {
491 | 806 |
                 XClass clazz = ( XClass ) i.next();
492 | 806 |
                 String qualifiedClassName = clazz.getQualifiedName();
493 |  |
494 | 806 |
                 if( qualifiedClassName.endsWith( suffix ) )
495 |  |
                 {
496 |  |
                     // perform sanity check for ambiguous imports
497 | 212 |
                     if( candidate != null && !candidate.equals( qualifiedClassName ) )
498 |  |
                     {
499 |  |
                         // ambiguous class import
500 | 0 |
                         throw new IllegalStateException( "In class " + getQualifiedName() + ": Ambiguous class:" + unqualifiedClassName + ". Is it " + candidate + " or " + qualifiedClassName + "?" );
501 |  |
                     }
502 |  |
                     else
503 |  |
                     {
504 | 212 |
                         candidate = qualifiedClassName;
505 |  |
                     }
506 |  |
                 }
507 |  |
             }
508 | 314 |
             return candidate;
509 |  |
         }
510 |  |
511 | 1944 |
         private final XClass unqualifiedNameInImportedClassesInnerClasses( final String unqualifiedClassName )
512 |  |
         {
513 | 1944 |
             if( !hasImportedClasses() )
514 |  |
             {
515 | 110 |
                 return null;
516 |  |
             }
517 |  |
518 | 1834 |
             XClass candidate = null;
519 |  |
520 | 1834 |
             for( Iterator i = getImportedClasses().iterator(); i.hasNext();  )
521 |  |
             {
522 | 5210 |
                 XClass clazz = ( XClass ) i.next();
523 |  |
524 |  |
                 // See if it's among the inner classes.
525 | 5210 |
                 for( Iterator inners = clazz.getInnerClasses().iterator(); inners.hasNext();  )
526 |  |
                 {
527 | 18 |
                     XClass inner = ( XClass ) inners.next();
528 | 18 |
                     boolean isAccessible = inner.isPublic();
529 |  |
530 | 18 |
                     if( inner.getName().equals( unqualifiedClassName ) && isAccessible )
531 |  |
                     {
532 | 6 |
                         if( candidate != null )
533 |  |
                         {
534 |  |
                             // ambiguous class import
535 | 0 |
                             throw new IllegalStateException( "In class " + getQualifiedName() + ": Ambiguous class:" + unqualifiedClassName + ". Is it " + candidate.getQualifiedName() + " or " + inner.getQualifiedName() + "?" );
536 |  |
                         }
537 |  |
                         else
538 |  |
                         {
539 | 6 |
                             candidate = inner;
540 |  |
                         }
541 |  |
                     }
542 |  |
                 }
543 |  |
             }
544 | 1834 |
             return candidate;
545 |  |
         }
546 |  |
547 |  |
         /**
548 |  |
          * Describe what the method does
549 |  |
          *
550 |  |
          * @param unqualifiedClassName  Describe what the parameter does
551 |  |
          * @return                      Describe the return value
552 |  |
          */
553 | 588 |
         private final String unqualifiedNameInInnerClasses( final String unqualifiedClassName )
554 |  |
         {
555 | 588 |
             if( !hasInnerClasses() )
556 |  |
             {
557 | 422 |
                 return null;
558 |  |
             }
559 |  |
560 | 166 |
             final String innerClassName = getQualifiedName() + '.' + unqualifiedClassName;
561 |  |
562 | 166 |
             String candidate = null;
563 |  |
564 | 166 |
             for( Iterator i = getInnerClasses().iterator(); i.hasNext();  )
565 |  |
             {
566 | 248 |
                 XClass innerClass = ( XClass ) i.next();
567 | 248 |
                 String qualifiedClassName = innerClass.getQualifiedName();
568 |  |
569 | 248 |
                 if( innerClassName.equals( qualifiedClassName ) )
570 |  |
                 {
571 | 46 |
                     candidate = qualifiedClassName;
572 | 46 |
                     break;
573 |  |
                 }
574 |  |
             }
575 | 166 |
             return candidate;
576 |  |
         }
577 |  |
578 |  |
         /**
579 |  |
          * Resolves Inner interfaces that exist in current class.
580 |  |
         *
581 |  |
         * This catches inner classes as well because isInterface()
582 |  |
         * does not indicate if it's an interface.
583 |  |
          *
584 |  |
          * @param unqualifiedClassName  Name of the class to resolve
585 |  |
          * @return                      The qualified name of the inner class.
586 |  |
          */
587 | 0 |
         private final String unqualifiedNameInInnerInterface( final String unqualifiedClassName )
588 |  |
         {
589 | 0 |
             String qualifiedClassName = getQualifiedName() + '$' + unqualifiedClassName;
590 | 0 |
             if (getXJavaDoc().classExists(qualifiedClassName)) {
591 |  |
     //            // The isInterface() method is not implemented for source classes.
592 |  |
     //            if (XJavaDoc.getInstance().getXClass(qualifiedClassName).isInterface()) {
593 |  |
     //                return getQualifiedName() + '.' + unqualifiedClassName;
594 |  |
     //            }
595 | 0 |
                 return getQualifiedName() + '.' + unqualifiedClassName;
596 |  |
             }
597 | 0 |
             return null;
598 |  |
         }
599 |  |
600 |  |
         /**
601 |  |
          * Resolves Inner classes that exist in the super class hierarchy.
602 |  |
          *
603 |  |
          * @param unqualifiedClassName  Name of the class to resolve
604 |  |
          * @return                      The qualified name of the inner class.
605 |  |
          */
606 | 0 |
         private final String unqualifiedNameInInnerClassesOfSuperClass( final String unqualifiedClassName )
607 |  |
         {
608 | 0 |
             XClass clazz = getXJavaDoc().getXClass(getQualifiedName());
609 | 0 |
             XClass superClazz = clazz.getSuperclass();
610 | 0 |
             while (superClazz != null && ! superClazz.getQualifiedName().equals("java.lang.Object")) {
611 | 0 |
                 String innerClassName = superClazz.getQualifiedName() + '.' + unqualifiedClassName;
612 | 0 |
                 for( Iterator i = superClazz.getInnerClasses().iterator(); i.hasNext();  )
613 |  |
                 {
614 | 0 |
                     XClass innerClass = ( XClass ) i.next();
615 | 0 |
                     String qualifiedClassName = innerClass.getQualifiedName();
616 | 0 |
                     if( innerClassName.equals( qualifiedClassName ) )
617 |  |
                     {
618 | 0 |
                         return qualifiedClassName;
619 |  |
                     }
620 |  |
                 }
621 | 0 |
                 superClazz = superClazz.getSuperclass();
622 |  |
             }
623 | 0 |
             return null;
624 |  |
         }
625 |  |
626 |  |
         /**
627 |  |
          * Describe what the method does
628 |  |
          *
629 |  |
          * @param unqualifiedClassName  Describe what the parameter does
630 |  |
          * @return                      Describe the return value
631 |  |
          */
632 | 122 |
         private final String unqualifiedNameInImportedPackages( final String unqualifiedClassName )
633 |  |
         {
634 | 122 |
             if( !hasImportedPackages() )
635 |  |
             {
636 | 0 |
                 return null;
637 |  |
             }
638 |  |
639 | 122 |
             final String suffix = "." + unqualifiedClassName;
640 | 122 |
             String candidate = null;
641 |  |
642 | 122 |
             for( Iterator i = getImportedPackages().iterator(); i.hasNext();  )
643 |  |
             {
644 | 182 |
                 String importedPackageName = ( ( XPackage ) i.next() ).getName();
645 | 182 |
                 String qualifiedClassName = importedPackageName + suffix;
646 |  |
647 | 182 |
                 if( getXJavaDoc().classExists( qualifiedClassName ) )
648 |  |
                 {
649 | 122 |
                     if( candidate != null && !candidate.equals( qualifiedClassName ) )
650 |  |
                     {
651 |  |
                         // ambiguous class import
652 | 0 |
                         throw new IllegalStateException( "In class " + getQualifiedName() + ": Ambiguous class:" + unqualifiedClassName + ". Is it " + candidate + " or " + qualifiedClassName + "?" );
653 |  |
                     }
654 |  |
                     else
655 |  |
                     {
656 | 122 |
                         candidate = qualifiedClassName;
657 |  |
                     }
658 |  |
                 }
659 |  |
             }
660 | 122 |
             return candidate;
661 |  |
         }
662 |  |
663 |  |
         /**
664 |  |
          * Returns the fully qualified class name if it's found in java.lang, otherwise
665 |  |
          * null.
666 |  |
          *
667 |  |
          * @param unqualifiedClassName
668 |  |
          * @return fully qualified class name, or null
669 |  |
          */
670 | 542 |
         private final String unqualifiedNameInJavaDotLang( final String unqualifiedClassName )
671 |  |
         {
672 | 542 |
             String qualifiedClassName = "java.lang." + unqualifiedClassName;
673 |  |
674 | 542 |
             if( getXJavaDoc().classExists( qualifiedClassName ) )
675 |  |
             {
676 | 208 |
                 return qualifiedClassName;
677 |  |
             }
678 |  |
             else
679 |  |
             {
680 | 334 |
                 return null;
681 |  |
             }
682 |  |
         }
683 |  |
684 |  |
         /**
685 |  |
          * Describe what the method does
686 |  |
          *
687 |  |
          * @param unqualifiedClassName  Describe what the parameter does
688 |  |
          * @return                      Describe the return value
689 |  |
          */
690 | 0 |
         private final String unqualifiedNameInTheSamePackage( final String unqualifiedClassName )
691 |  |
         {
692 | 0 |
             String qualifiedClassName;
693 |  |
694 | 0 |
             if( getContainingPackage().getName().equals( "" ) )
695 |  |
             {
696 | 0 |
                 qualifiedClassName = unqualifiedClassName;
697 |  |
             }
698 |  |
             else
699 |  |
             {
700 | 0 |
                 qualifiedClassName = getContainingPackage().getName() + '.' + unqualifiedClassName;
701 |  |
             }
702 |  |
703 | 0 |
             if( getXJavaDoc().classExists( qualifiedClassName ) )
704 |  |
             {
705 | 0 |
                 return qualifiedClassName;
706 |  |
             }
707 |  |
             else
708 |  |
             {
709 | 0 |
                 return null;
710 |  |
             }
711 |  |
712 |  |
         }
713 |  |
714 | 1048 |
         private final String unqualifiedNameInTheSameClassAsAnInnerClass( final String unqualifiedClassName )
715 |  |
         {
716 |  |
             //containing class=com.p.A, inner-reference=B ->com.p.A.B
717 | 1048 |
             String qualifiedClassName = getQualifiedName() + '.' + unqualifiedClassName;
718 |  |
719 | 1048 |
             if( getXJavaDoc().classExists( qualifiedClassName ) )
720 | 0 |
                 return qualifiedClassName;
721 |  |
722 |  |
             //containing class=com.p.A, inner-reference=A.B ->com.p.A.B
723 | 1048 |
             if( getContainingPackage().getName().equals( "" ) )
724 |  |
             {
725 | 196 |
                 qualifiedClassName = unqualifiedClassName;
726 |  |
             }
727 |  |
             else
728 |  |
             {
729 | 852 |
                 qualifiedClassName = getContainingPackage().getName() + '.' + unqualifiedClassName;
730 |  |
             }
731 |  |
732 | 1048 |
             if( getXJavaDoc().classExists( qualifiedClassName ) )
733 | 460 |
                 return qualifiedClassName;
734 |  |
735 | 588 |
             return null;
736 |  |
         }
737 |  |
738 |  |
         /**
739 |  |
          * Describe what the method does
740 |  |
          *
741 |  |
          * @param useNodeParser  Describe what the parameter does
742 |  |
          */
743 | 684 |
         private void parse( boolean useNodeParser )
744 |  |
         {
745 | 684 |
             try
746 |  |
             {
747 | 684 |
                 if( useNodeParser )
748 |  |
                 {
749 |  |
                     // We need a pool of parsers, because parsing one file
750 |  |
                     // might kick away the parsing of another etc.
751 |  |
     //                _nodeParser.populate( this );
752 | 12 |
                     new NodeParser( getXJavaDoc(), getTagFactory() ).populate( this );
753 |  |
                 }
754 |  |
                 else
755 |  |
                 {
756 |  |
     //                _simpleParser.populate( this );
757 | 672 |
                     new SimpleParser( getXJavaDoc(), getTagFactory() ).populate( this );
758 |  |
                 }
759 |  |
             }
760 |  |
             catch( ParseException e )
761 |  |
             {
762 |  |
                 // Source code is bad. Not according to grammar. User's fault.
763 | 0 |
                 String cls = _sourceFile != null ? _sourceFile.toString() : getQualifiedName();
764 |  |
765 | 0 |
                 System.err.println( "Error parsing " + cls + ':' + e.getMessage() );
766 |  |
             }
767 |  |
             catch( TokenMgrError e )
768 |  |
             {
769 | 0 |
                 String cls = _sourceFile != null ? _sourceFile.toString() : getQualifiedName();
770 |  |
771 | 0 |
                 System.err.println( "Error parsing " + cls + ':' + e.getMessage() );
772 |  |
             }
773 |  |
         }
774 |  |
     }
775 |  |