home *** CD-ROM | disk | FTP | other *** search
Java Source | 1999-09-19 | 9.2 KB | 301 lines |
- /*
- * @(#)ClassUseMapper.java 1.2 98/06/30
- *
- * Copyright 1998 by Sun Microsystems, Inc.,
- * 901 San Antonio Road, Palo Alto, California, 94303, U.S.A.
- * All rights reserved.
- *
- * This software is the confidential and proprietary information
- * of Sun Microsystems, Inc. ("Confidential Information"). You
- * shall not disclose such Confidential Information and shall use
- * it only in accordance with the terms of the license agreement
- * you entered into with Sun.
- */
-
- package com.sun.tools.doclets.standard;
-
- import com.sun.javadoc.*;
- import com.sun.tools.doclets.ClassTree;
- import com.sun.tools.doclets.DocletAbortException;
- import java.util.*;
-
- /**
- * @since JDK1.2
- * @author Robert G. Field
- */
- public class ClassUseMapper {
-
- private final ClassTree classtree;
-
- /**
- * Mapping of ClassDocs to set of PackageDoc used by that class.
- * Entries may be null.
- */
- public Map classToPackage = new HashMap();
-
- /**
- * Mapping of ClassDocs to set of ClassDoc used by that class.
- * Entries may be null.
- */
- public Map classToClass = new HashMap();
-
- /**
- * Mapping of ClassDocs to list of ClassDoc which are direct or
- * indirect subclasses of that class.
- * Entries may be null.
- */
- public Map classToSubclass = new HashMap();
-
- /**
- * Mapping of ClassDocs to list of ClassDoc which are direct or
- * indirect subinterfaces of that interface.
- * Entries may be null.
- */
- public Map classToSubinterface = new HashMap();
-
- /**
- * Mapping of ClassDocs to list of ClassDoc which implement
- * this interface.
- * Entries may be null.
- */
- public Map classToImplementingClass = new HashMap();
-
- /**
- * Mapping of ClassDocs to list of FieldDoc declared as that class.
- * Entries may be null.
- */
- public Map classToField = new HashMap();
-
- /**
- * Mapping of ClassDocs to list of MethodDoc returning that class.
- * Entries may be null.
- */
- public Map classToMethodReturn = new HashMap();
-
- /**
- * Mapping of ClassDocs to list of MethodDoc having that class
- * as an arg.
- * Entries may be null.
- */
- public Map classToMethodArgs = new HashMap();
-
- /**
- * Mapping of ClassDocs to list of MethodDoc which throws that class.
- * Entries may be null.
- */
- public Map classToMethodThrows = new HashMap();
-
- /**
- * Mapping of ClassDocs to list of ConstructorDoc having that class
- * as an arg.
- * Entries may be null.
- */
- public Map classToConstructorArgs = new HashMap();
-
- /**
- * Mapping of ClassDocs to list of ConstructorDoc which throws that class.
- * Entries may be null.
- */
- public Map classToConstructorThrows = new HashMap();
-
-
- /**
- * Write out class use pages.
- */
- public static void generate(RootDoc root,
- ClassTree classtree) throws DocletAbortException {
- ClassUseMapper mapper = new ClassUseMapper(root, classtree);
- ClassDoc[] classes = root.classes();
- for (int i = 0; i < classes.length; i++) {
- ClassUseWriter.generate(mapper, classes[i]);
- }
- PackageDoc[] pkgs = Standard.configuration().packages;
- for (int i = 0; i < pkgs.length; i++) {
- PackageUseWriter.generate(mapper, pkgs[i]);
- }
- }
-
- private ClassUseMapper(RootDoc root, ClassTree classtree) {
- this.classtree = classtree;
-
- // Map subclassing, subinterfacing implementing, ...
- for (Iterator it = classtree.baseclasses().iterator(); it.hasNext();) {
- subclasses((ClassDoc)it.next());
- }
- for (Iterator it = classtree.baseinterfaces().iterator(); it.hasNext();) {
- // does subinterfacing as side-effect
- implementingClasses((ClassDoc)it.next());
- }
- // Map methods, fields, constructors using a class.
- ClassDoc[] classes = root.classes();
- for (int i = 0; i < classes.length; i++) {
- ClassDoc cd = classes[i];
- FieldDoc[] fields = cd.fields();
- for (int j = 0; j < fields.length; j++) {
- FieldDoc fd = fields[j];
- ClassDoc tcd = fd.type().asClassDoc();
- if (tcd != null) {
- add(classToField, tcd, fd);
- }
- }
- ConstructorDoc[] cons = cd.constructors();
- for (int j = 0; j < cons.length; j++) {
- mapExecutable(cons[j]);
- }
- MethodDoc[] meths = cd.methods();
- for (int j = 0; j < meths.length; j++) {
- MethodDoc md = meths[j];
- mapExecutable(md);
- ClassDoc tcd = md.returnType().asClassDoc();
- if (tcd != null) {
- add(classToMethodReturn, tcd, md);
- }
- }
- }
- }
-
- /**
- * Return all subclasses of a class AND fill-in classToSubclass map.
- */
- private Collection subclasses(ClassDoc cd) {
- Collection ret = (Collection)classToSubclass.get(cd);
- if (ret == null) {
- ret = new TreeSet();
- List subs = classtree.subclasses(cd);
- if (subs != null) {
- ret.addAll(subs);
- for (Iterator it = subs.iterator(); it.hasNext();) {
- ret.addAll(subclasses((ClassDoc)it.next()));
- }
- }
- addAll(classToSubclass, cd, ret);
- }
- return ret;
- }
-
- /**
- * Return all subinterfaces of an interface AND fill-in classToSubinterface map.
- */
- private Collection subinterfaces(ClassDoc cd) {
- Collection ret = (Collection)classToSubinterface.get(cd);
- if (ret == null) {
- ret = new TreeSet();
- List subs = classtree.subinterfaces(cd);
- if (subs != null) {
- ret.addAll(subs);
- for (Iterator it = subs.iterator(); it.hasNext();) {
- ret.addAll(subinterfaces((ClassDoc)it.next()));
- }
- }
- addAll(classToSubinterface, cd, ret);
- }
- return ret;
- }
-
- /**
- * Return all implementing classes of an interface (including
- * all subclasses of implementing classes and all classes
- * implementing subinterfaces) AND fill-in both classToImplementingClass
- * and classToSubinterface maps.
- */
- private Collection implementingClasses(ClassDoc cd) {
- Collection ret = (List)classToImplementingClass.get(cd);
- if (ret == null) {
- ret = new TreeSet();
- List impl = classtree.implementingclasses(cd);
- if (impl != null) {
- ret.addAll(impl);
- for (Iterator it = impl.iterator(); it.hasNext();) {
- ret.addAll(subclasses((ClassDoc)it.next()));
- }
- }
- for (Iterator it = subinterfaces(cd).iterator(); it.hasNext();) {
- ret.addAll(implementingClasses((ClassDoc)it.next()));
- }
- addAll(classToImplementingClass, cd, ret);
- }
- return ret;
- }
-
- /**
- * Determine classes used by a method or constructor, so they can be
- * inverse mapped.
- */
- private void mapExecutable(ExecutableMemberDoc em) {
- Parameter[] params = em.parameters();
- boolean isConstructor = em.isConstructor();
- List classArgs = new ArrayList();
- for (int k = 0; k < params.length; k++) {
- ClassDoc pcd = params[k].type().asClassDoc();
- // primitives don't get mapped, also avoid dups
- if (pcd != null && !classArgs.contains(pcd)) {
- add(isConstructor? classToConstructorArgs :classToMethodArgs,
- pcd, em);
- classArgs.add(pcd);
- }
- }
- ClassDoc[] thr = em.thrownExceptions();
- for (int k = 0; k < thr.length; k++) {
- add(isConstructor? classToConstructorThrows : classToMethodThrows,
- thr[k], em);
- }
- }
-
- private List refList(Map map, ClassDoc cd) {
- List list = (List)map.get(cd);
- if (list == null) {
- list = new ArrayList();
- map.put(cd, list);
- }
- return list;
- }
-
- private Set packageSet(ClassDoc cd) {
- Set pkgSet = (Set)classToPackage.get(cd);
- if (pkgSet == null) {
- pkgSet = new TreeSet();
- classToPackage.put(cd, pkgSet);
- }
- return pkgSet;
- }
-
- private Set classSet(ClassDoc cd) {
- Set clsSet = (Set)classToClass.get(cd);
- if (clsSet == null) {
- clsSet = new TreeSet();
- classToClass.put(cd, clsSet);
- }
- return clsSet;
- }
-
- private void add(Map map, ClassDoc cd, ProgramElementDoc ref) {
- // add to specified map
- refList(map, cd).add(ref);
-
- // add ref's package to package map and class map
- packageSet(cd).add(ref.containingPackage());
- classSet(cd).add(ref instanceof MemberDoc?
- ((MemberDoc)ref).containingClass() :
- ref);
- }
-
- private void addAll(Map map, ClassDoc cd, Collection refs) {
- if (refs == null) {
- return;
- }
- // add to specified map
- refList(map, cd).addAll(refs);
-
- Set pkgSet = packageSet(cd);
- Set clsSet = classSet(cd);
- // add ref's package to package map and class map
- for (Iterator it = refs.iterator(); it.hasNext();) {
- ProgramElementDoc pedoc = (ProgramElementDoc)it.next();
- pkgSet.add(pedoc.containingPackage());
- clsSet.add(pedoc instanceof MemberDoc?
- ((MemberDoc)pedoc).containingClass() :
- pedoc);
- }
- }
- }
-