Wed, 31 Oct 2012 13:48:15 -0700
8001664: refactor javadoc to use abstraction to handle files
Reviewed-by: darcy
1.1 --- a/src/share/classes/com/sun/tools/doclets/formats/html/ConfigurationImpl.java Wed Oct 31 08:31:40 2012 -0700 1.2 +++ b/src/share/classes/com/sun/tools/doclets/formats/html/ConfigurationImpl.java Wed Oct 31 13:48:15 2012 -0700 1.3 @@ -25,7 +25,6 @@ 1.4 1.5 package com.sun.tools.doclets.formats.html; 1.6 1.7 -import java.io.*; 1.8 import java.net.*; 1.9 import java.util.*; 1.10 1.11 @@ -46,6 +45,11 @@ 1.12 * use "-helpfile" option when already "-nohelp" option is used. 1.13 * </p> 1.14 * 1.15 + * <p><b>This is NOT part of any supported API. 1.16 + * If you write code that depends on this, you do so at your own risk. 1.17 + * This code and its internal interfaces are subject to change or 1.18 + * deletion without notice.</b> 1.19 + * 1.20 * @author Robert Field. 1.21 * @author Atul Dambalkar. 1.22 * @author Jamie Ho 1.23 @@ -362,7 +366,7 @@ 1.24 "-helpfile")); 1.25 return false; 1.26 } 1.27 - File help = new File(os[1]); 1.28 + DocFile help = DocFile.createFileForInput(this, os[1]); 1.29 if (!help.exists()) { 1.30 reporter.printError(getText("doclet.File_not_found", os[1])); 1.31 return false;
2.1 --- a/src/share/classes/com/sun/tools/doclets/formats/html/HtmlDoclet.java Wed Oct 31 08:31:40 2012 -0700 2.2 +++ b/src/share/classes/com/sun/tools/doclets/formats/html/HtmlDoclet.java Wed Oct 31 13:48:15 2012 -0700 2.3 @@ -104,15 +104,12 @@ 2.4 return; 2.5 } 2.6 boolean nodeprecated = configuration.nodeprecated; 2.7 - String configdestdir = configuration.destDirName; 2.8 - String confighelpfile = configuration.helpfile; 2.9 - String configstylefile = configuration.stylesheetfile; 2.10 - performCopy(configdestdir, confighelpfile); 2.11 - performCopy(configdestdir, configstylefile); 2.12 - Util.copyResourceFile(configuration, "background.gif", false); 2.13 - Util.copyResourceFile(configuration, "tab.gif", false); 2.14 - Util.copyResourceFile(configuration, "titlebar.gif", false); 2.15 - Util.copyResourceFile(configuration, "titlebar_end.gif", false); 2.16 + performCopy(configuration.helpfile); 2.17 + performCopy(configuration.stylesheetfile); 2.18 + copyResourceFile("background.gif"); 2.19 + copyResourceFile("tab.gif"); 2.20 + copyResourceFile("titlebar.gif"); 2.21 + copyResourceFile("titlebar_end.gif"); 2.22 // do early to reduce memory footprint 2.23 if (configuration.classuse) { 2.24 ClassUseWriter.generate(configuration, classtree); 2.25 @@ -149,8 +146,8 @@ 2.26 // If a stylesheet file is not specified, copy the default stylesheet 2.27 // and replace newline with platform-specific newline. 2.28 if (configuration.stylesheetfile.length() == 0) { 2.29 - Util.copyFile(configuration, "stylesheet.css", DocPaths.RESOURCES, 2.30 - DocPath.empty, false, true); 2.31 + DocFile f = DocFile.createFileForOutput(configuration, DocPaths.STYLESHEET); 2.32 + f.copyResource(DocPaths.RESOURCES.resolve(DocPaths.STYLESHEET), false, true); 2.33 } 2.34 } 2.35 2.36 @@ -251,29 +248,33 @@ 2.37 return (ConfigurationImpl.getInstance()).validOptions(options, reporter); 2.38 } 2.39 2.40 - private void performCopy(String configdestdir, String filename) { 2.41 + /** 2.42 + * Copy a file in the resources directory to the destination directory. 2.43 + * @param resource The name of the resource file to copy 2.44 + */ 2.45 + private void copyResourceFile(String resource) { 2.46 + DocPath p = DocPaths.RESOURCES.resolve(resource); 2.47 + DocFile f = DocFile.createFileForOutput(configuration, p); 2.48 + f.copyResource(p, false, false); 2.49 + } 2.50 + 2.51 + private void performCopy(String filename) { 2.52 + if (filename.isEmpty()) 2.53 + return; 2.54 + 2.55 try { 2.56 - String destdir = (configdestdir.length() > 0) ? 2.57 - configdestdir + File.separatorChar: ""; 2.58 - if (filename.length() > 0) { 2.59 - File helpstylefile = new File(filename); 2.60 - String parent = helpstylefile.getParent(); 2.61 - String helpstylefilename = (parent == null)? 2.62 - filename: 2.63 - filename.substring(parent.length() + 1); 2.64 - File desthelpfile = new File(destdir + helpstylefilename); 2.65 - if (!desthelpfile.getCanonicalPath().equals( 2.66 - helpstylefile.getCanonicalPath())) { 2.67 - configuration.message. 2.68 - notice((SourcePosition) null, 2.69 - "doclet.Copying_File_0_To_File_1", 2.70 - helpstylefile.toString(), desthelpfile.toString()); 2.71 - Util.copyFile(desthelpfile, helpstylefile); 2.72 - } 2.73 - } 2.74 + DocFile fromfile = DocFile.createFileForInput(configuration, filename); 2.75 + DocPath path = DocPath.create(fromfile.getName()); 2.76 + DocFile toFile = DocFile.createFileForOutput(configuration, path); 2.77 + if (toFile.isSameFile(fromfile)) 2.78 + return; 2.79 + 2.80 + configuration.message.notice((SourcePosition) null, 2.81 + "doclet.Copying_File_0_To_File_1", 2.82 + fromfile.toString(), path.getPath()); 2.83 + toFile.copyFile(fromfile); 2.84 } catch (IOException exc) { 2.85 - configuration.message. 2.86 - error((SourcePosition) null, 2.87 + configuration.message.error((SourcePosition) null, 2.88 "doclet.perform_copy_exception_encountered", 2.89 exc.toString()); 2.90 throw new DocletAbortException();
3.1 --- a/src/share/classes/com/sun/tools/doclets/formats/html/HtmlDocletWriter.java Wed Oct 31 08:31:40 2012 -0700 3.2 +++ b/src/share/classes/com/sun/tools/doclets/formats/html/HtmlDocletWriter.java Wed Oct 31 13:48:15 2012 -0700 3.3 @@ -723,7 +723,8 @@ 3.4 if (helpfile.isEmpty()) { 3.5 helpfilenm = DocPaths.HELP_DOC; 3.6 } else { 3.7 - helpfilenm = DocPath.create(new File(helpfile).getName()); 3.8 + DocFile file = DocFile.createFileForInput(configuration, helpfile); 3.9 + helpfilenm = DocPath.create(file.getName()); 3.10 } 3.11 Content linkContent = getHyperLink(pathToRoot.resolve(helpfilenm), 3.12 helpLabel, "", ""); 3.13 @@ -1671,12 +1672,13 @@ 3.14 * @return an HtmlTree for the lINK tag which provides the stylesheet location 3.15 */ 3.16 public HtmlTree getStyleSheetProperties() { 3.17 - String filename = configuration.stylesheetfile; 3.18 + String stylesheetfile = configuration.stylesheetfile; 3.19 DocPath stylesheet; 3.20 - if (filename.length() > 0) { 3.21 - stylesheet = DocPath.create(new File(filename).getName()); 3.22 + if (stylesheetfile.isEmpty()) { 3.23 + stylesheet = DocPaths.STYLESHEET; 3.24 } else { 3.25 - stylesheet = DocPaths.STYLESHEET; 3.26 + DocFile file = DocFile.createFileForInput(configuration, stylesheetfile); 3.27 + stylesheet = DocPath.create(file.getName()); 3.28 } 3.29 HtmlTree link = HtmlTree.LINK("stylesheet", "text/css", 3.30 pathToRoot.resolve(stylesheet).getPath(),
4.1 --- a/src/share/classes/com/sun/tools/doclets/formats/html/SourceToHTMLConverter.java Wed Oct 31 08:31:40 2012 -0700 4.2 +++ b/src/share/classes/com/sun/tools/doclets/formats/html/SourceToHTMLConverter.java Wed Oct 31 13:48:15 2012 -0700 4.3 @@ -26,11 +26,13 @@ 4.4 package com.sun.tools.doclets.formats.html; 4.5 4.6 import java.io.*; 4.7 + 4.8 import javax.tools.FileObject; 4.9 + 4.10 import com.sun.javadoc.*; 4.11 +import com.sun.tools.doclets.formats.html.markup.*; 4.12 import com.sun.tools.doclets.internal.toolkit.*; 4.13 import com.sun.tools.doclets.internal.toolkit.util.*; 4.14 -import com.sun.tools.doclets.formats.html.markup.*; 4.15 4.16 /** 4.17 * Converts Java Source Code to HTML. 4.18 @@ -95,8 +97,7 @@ 4.19 // package files to HTML. 4.20 if (!(configuration.nodeprecated && 4.21 (Util.isDeprecated(cds[i]) || Util.isDeprecated(cds[i].containingPackage())))) 4.22 - convertClass(configuration, cds[i], 4.23 - getPackageOutputDir(outputdir, cds[i].containingPackage())); 4.24 + convertClass(configuration, cds[i], outputdir); 4.25 } 4.26 } 4.27 4.28 @@ -109,10 +110,9 @@ 4.29 */ 4.30 public static void convertPackage(ConfigurationImpl configuration, PackageDoc pd, 4.31 DocPath outputdir) { 4.32 - if (pd == null || outputdir == null) { 4.33 + if (pd == null) { 4.34 return; 4.35 } 4.36 - DocPath classOutputdir = getPackageOutputDir(outputdir, pd); 4.37 ClassDoc[] cds = pd.allClasses(); 4.38 for (int i = 0; i < cds.length; i++) { 4.39 // If -nodeprecated option is set and the class is marked as deprecated, 4.40 @@ -120,22 +120,11 @@ 4.41 // containing package deprecation since it is already check in 4.42 // the calling method above. 4.43 if (!(configuration.nodeprecated && Util.isDeprecated(cds[i]))) 4.44 - convertClass(configuration, cds[i], classOutputdir); 4.45 + convertClass(configuration, cds[i], outputdir); 4.46 } 4.47 } 4.48 4.49 /** 4.50 - * Return the directory write output to for the given package. 4.51 - * 4.52 - * @param outputDir the directory to output to. 4.53 - * @param pd the Package to generate output for. 4.54 - * @return the package output directory as a String. 4.55 - */ 4.56 - private static DocPath getPackageOutputDir(DocPath outputDir, PackageDoc pd) { 4.57 - return outputDir.resolve(DocPath.forPackage(pd)); 4.58 - } 4.59 - 4.60 - /** 4.61 * Convert the given Class to an HTML. 4.62 * 4.63 * @param configuration the configuration. 4.64 @@ -144,7 +133,7 @@ 4.65 */ 4.66 public static void convertClass(ConfigurationImpl configuration, ClassDoc cd, 4.67 DocPath outputdir) { 4.68 - if (cd == null || outputdir == null) { 4.69 + if (cd == null) { 4.70 return; 4.71 } 4.72 try { 4.73 @@ -184,8 +173,8 @@ 4.74 addBlankLines(pre); 4.75 Content div = HtmlTree.DIV(HtmlStyle.sourceContainer, pre); 4.76 body.addContent(div); 4.77 - writeToFile(body, outputdir, cd.name(), configuration); 4.78 - } catch (Exception e){ 4.79 + writeToFile(body, outputdir.resolve(DocPath.forClass(cd)), configuration); 4.80 + } catch (IOException e) { 4.81 e.printStackTrace(); 4.82 } 4.83 } 4.84 @@ -194,12 +183,11 @@ 4.85 * Write the output to the file. 4.86 * 4.87 * @param body the documentation content to be written to the file. 4.88 - * @param outputDir the directory to output to. 4.89 - * @param className the name of the class that I am converting to HTML. 4.90 + * @param path the path for the file. 4.91 * @param configuration the Doclet configuration to pass notices to. 4.92 */ 4.93 - private static void writeToFile(Content body, DocPath outputDir, 4.94 - String className, ConfigurationImpl configuration) throws IOException { 4.95 + private static void writeToFile(Content body, DocPath path, 4.96 + ConfigurationImpl configuration) throws IOException { 4.97 Content htmlDocType = DocType.Transitional(); 4.98 Content head = new HtmlTree(HtmlTag.HEAD); 4.99 head.addContent(HtmlTree.TITLE(new StringContent( 4.100 @@ -208,15 +196,15 @@ 4.101 Content htmlTree = HtmlTree.HTML(configuration.getLocale().getLanguage(), 4.102 head, body); 4.103 Content htmlDocument = new HtmlDocument(htmlDocType, htmlTree); 4.104 - File dir = outputDir.resolveAgainst(configuration.destDirName); 4.105 - dir.mkdirs(); 4.106 - File newFile = new File(dir, className + ".html"); 4.107 - configuration.message.notice("doclet.Generating_0", newFile.getPath()); 4.108 - FileOutputStream fout = new FileOutputStream(newFile); 4.109 - BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(fout)); 4.110 - bw.write(htmlDocument.toString()); 4.111 - bw.close(); 4.112 - fout.close(); 4.113 + configuration.message.notice("doclet.Generating_0", path.getPath()); 4.114 + DocFile df = DocFile.createFileForOutput(configuration, path); 4.115 + Writer w = df.openWriter(); 4.116 + try { 4.117 + htmlDocument.write(w, true); 4.118 + } finally { 4.119 + w.close(); 4.120 + } 4.121 + 4.122 } 4.123 4.124 /** 4.125 @@ -229,7 +217,8 @@ 4.126 String filename = configuration.stylesheetfile; 4.127 DocPath stylesheet; 4.128 if (filename.length() > 0) { 4.129 - stylesheet = DocPath.create(new File(filename).getName()); 4.130 + DocFile file = DocFile.createFileForInput(configuration, filename); 4.131 + stylesheet = DocPath.create(file.getName()); 4.132 } else { 4.133 stylesheet = DocPaths.STYLESHEET; 4.134 }
5.1 --- a/src/share/classes/com/sun/tools/doclets/formats/html/markup/HtmlWriter.java Wed Oct 31 08:31:40 2012 -0700 5.2 +++ b/src/share/classes/com/sun/tools/doclets/formats/html/markup/HtmlWriter.java Wed Oct 31 13:48:15 2012 -0700 5.3 @@ -156,7 +156,7 @@ 5.4 */ 5.5 public HtmlWriter(Configuration configuration, DocPath path) 5.6 throws IOException, UnsupportedEncodingException { 5.7 - writer = Util.genWriter(configuration, path); 5.8 + writer = DocFile.createFileForOutput(configuration, path).openWriter(); 5.9 this.configuration = configuration; 5.10 this.memberDetailsListPrinted = false; 5.11 packageTableHeader = new String[] {
6.1 --- a/src/share/classes/com/sun/tools/doclets/internal/toolkit/AbstractDoclet.java Wed Oct 31 08:31:40 2012 -0700 6.2 +++ b/src/share/classes/com/sun/tools/doclets/internal/toolkit/AbstractDoclet.java Wed Oct 31 13:48:15 2012 -0700 6.3 @@ -106,7 +106,7 @@ 6.4 6.5 /** 6.6 * Start the generation of files. Call generate methods in the individual 6.7 - * writers, which will in turn genrate the documentation files. Call the 6.8 + * writers, which will in turn generate the documentation files. Call the 6.9 * TreeWriter generation first to ensure the Class Hierarchy is built 6.10 * first and then can be used in the later generation. 6.11 * 6.12 @@ -124,17 +124,7 @@ 6.13 ClassTree classtree = new ClassTree(configuration, configuration.nodeprecated); 6.14 6.15 generateClassFiles(root, classtree); 6.16 - if (configuration.sourcepath != null && configuration.sourcepath.length() > 0) { 6.17 - StringTokenizer pathTokens = new StringTokenizer(configuration.sourcepath, 6.18 - String.valueOf(File.pathSeparatorChar)); 6.19 - boolean first = true; 6.20 - while(pathTokens.hasMoreTokens()){ 6.21 - Util.copyDocFiles(configuration, 6.22 - new File(pathTokens.nextToken()), 6.23 - DocPaths.DOC_FILES, first); 6.24 - first = false; 6.25 - } 6.26 - } 6.27 + Util.copyDocFiles(configuration, DocPaths.DOC_FILES); 6.28 6.29 PackageListWriter.generate(configuration); 6.30 generatePackageFiles(classtree);
7.1 --- a/src/share/classes/com/sun/tools/doclets/internal/toolkit/Configuration.java Wed Oct 31 08:31:40 2012 -0700 7.2 +++ b/src/share/classes/com/sun/tools/doclets/internal/toolkit/Configuration.java Wed Oct 31 13:48:15 2012 -0700 7.3 @@ -456,7 +456,7 @@ 7.4 tagletManager.addCustomTag(args[1], tagletpath); 7.5 continue; 7.6 } 7.7 - String[] tokens = Util.tokenize(args[1], 7.8 + String[] tokens = tokenize(args[1], 7.9 TagletManager.SIMPLE_TAGLET_OPT_SEPERATOR, 3); 7.10 if (tokens.length == 1) { 7.11 String tagName = args[1]; 7.12 @@ -480,6 +480,47 @@ 7.13 } 7.14 } 7.15 7.16 + /** 7.17 + * Given a string, return an array of tokens. The separator can be escaped 7.18 + * with the '\' character. The '\' character may also be escaped by the 7.19 + * '\' character. 7.20 + * 7.21 + * @param s the string to tokenize. 7.22 + * @param separator the separator char. 7.23 + * @param maxTokens the maximum number of tokens returned. If the 7.24 + * max is reached, the remaining part of s is appended 7.25 + * to the end of the last token. 7.26 + * 7.27 + * @return an array of tokens. 7.28 + */ 7.29 + private String[] tokenize(String s, char separator, int maxTokens) { 7.30 + List<String> tokens = new ArrayList<String>(); 7.31 + StringBuilder token = new StringBuilder (); 7.32 + boolean prevIsEscapeChar = false; 7.33 + for (int i = 0; i < s.length(); i += Character.charCount(i)) { 7.34 + int currentChar = s.codePointAt(i); 7.35 + if (prevIsEscapeChar) { 7.36 + // Case 1: escaped character 7.37 + token.appendCodePoint(currentChar); 7.38 + prevIsEscapeChar = false; 7.39 + } else if (currentChar == separator && tokens.size() < maxTokens-1) { 7.40 + // Case 2: separator 7.41 + tokens.add(token.toString()); 7.42 + token = new StringBuilder(); 7.43 + } else if (currentChar == '\\') { 7.44 + // Case 3: escape character 7.45 + prevIsEscapeChar = true; 7.46 + } else { 7.47 + // Case 4: regular character 7.48 + token.appendCodePoint(currentChar); 7.49 + } 7.50 + } 7.51 + if (token.length() > 0) { 7.52 + tokens.add(token.toString()); 7.53 + } 7.54 + return tokens.toArray(new String[] {}); 7.55 + } 7.56 + 7.57 private void addToSet(Set<String> s, String str){ 7.58 StringTokenizer st = new StringTokenizer(str, ":"); 7.59 String current; 7.60 @@ -532,12 +573,12 @@ 7.61 String opt = os[0].toLowerCase(); 7.62 if (opt.equals("-d")) { 7.63 String destdirname = addTrailingFileSep(os[1]); 7.64 - File destDir = new File(destdirname); 7.65 + DocFile destDir = DocFile.createFileForDirectory(this, destdirname); 7.66 if (!destDir.exists()) { 7.67 //Create the output directory (in case it doesn't exist yet) 7.68 reporter.printNotice(getText("doclet.dest_dir_create", 7.69 destdirname)); 7.70 - (new File(destdirname)).mkdirs(); 7.71 + destDir.mkdirs(); 7.72 } else if (!destDir.isDirectory()) { 7.73 reporter.printError(getText( 7.74 "doclet.destination_directory_not_directory_0", 7.75 @@ -711,7 +752,7 @@ 7.76 public InputStream getBuilderXML() throws FileNotFoundException { 7.77 return builderXMLPath == null ? 7.78 Configuration.class.getResourceAsStream(DEFAULT_BUILDER_XML) : 7.79 - new FileInputStream(new File(builderXMLPath)); 7.80 + DocFile.createFileForInput(this, builderXMLPath).openInputStream(); 7.81 } 7.82 7.83 /**
8.1 --- a/src/share/classes/com/sun/tools/doclets/internal/toolkit/builders/AnnotationTypeBuilder.java Wed Oct 31 08:31:40 2012 -0700 8.2 +++ b/src/share/classes/com/sun/tools/doclets/internal/toolkit/builders/AnnotationTypeBuilder.java Wed Oct 31 13:48:15 2012 -0700 8.3 @@ -140,10 +140,7 @@ 8.4 //Only copy doc files dir if the containing package is not 8.5 //documented AND if we have not documented a class from the same 8.6 //package already. Otherwise, we are making duplicate copies. 8.7 - Util.copyDocFiles(configuration, 8.8 - new File(Util.getPackageSourcePath(configuration, containingPackage), 8.9 - DocPath.forPackage(annotationTypeDoc).getPath()), 8.10 - DocPaths.DOC_FILES, true); 8.11 + Util.copyDocFiles(configuration, containingPackage); 8.12 containingPackagesSeen.add(containingPackage.name()); 8.13 } 8.14 }
9.1 --- a/src/share/classes/com/sun/tools/doclets/internal/toolkit/builders/ClassBuilder.java Wed Oct 31 08:31:40 2012 -0700 9.2 +++ b/src/share/classes/com/sun/tools/doclets/internal/toolkit/builders/ClassBuilder.java Wed Oct 31 13:48:15 2012 -0700 9.3 @@ -266,10 +266,7 @@ 9.4 //Only copy doc files dir if the containing package is not 9.5 //documented AND if we have not documented a class from the same 9.6 //package already. Otherwise, we are making duplicate copies. 9.7 - Util.copyDocFiles(configuration, 9.8 - new File(Util.getPackageSourcePath(configuration, containingPackage), 9.9 - DocPath.forPackage(classDoc).getPath()), 9.10 - DocPaths.DOC_FILES, true); 9.11 + Util.copyDocFiles(configuration, containingPackage); 9.12 containingPackagesSeen.add(containingPackage.name()); 9.13 } 9.14 }
10.1 --- a/src/share/classes/com/sun/tools/doclets/internal/toolkit/builders/PackageSummaryBuilder.java Wed Oct 31 08:31:40 2012 -0700 10.2 +++ b/src/share/classes/com/sun/tools/doclets/internal/toolkit/builders/PackageSummaryBuilder.java Wed Oct 31 13:48:15 2012 -0700 10.3 @@ -119,11 +119,7 @@ 10.4 packageWriter.addPackageFooter(contentTree); 10.5 packageWriter.printDocument(contentTree); 10.6 packageWriter.close(); 10.7 - Util.copyDocFiles( 10.8 - configuration, 10.9 - Util.getPackageSourcePath(configuration, packageDoc), 10.10 - DocPath.forPackage(packageDoc).resolve(DocPaths.DOC_FILES), 10.11 - true); 10.12 + Util.copyDocFiles(configuration, packageDoc); 10.13 } 10.14 10.15 /**
11.1 --- a/src/share/classes/com/sun/tools/doclets/internal/toolkit/taglets/TagletManager.java Wed Oct 31 08:31:40 2012 -0700 11.2 +++ b/src/share/classes/com/sun/tools/doclets/internal/toolkit/taglets/TagletManager.java Wed Oct 31 13:48:15 2012 -0700 11.3 @@ -161,7 +161,7 @@ 11.4 * @param message the message retriever to print warnings. 11.5 */ 11.6 public TagletManager(boolean nosince, boolean showversion, 11.7 - boolean showauthor, MessageRetriever message){ 11.8 + boolean showauthor, MessageRetriever message) { 11.9 overridenStandardTags = new HashSet<String>(); 11.10 potentiallyConflictingTags = new HashSet<String>(); 11.11 standardTags = new HashSet<String>(); 11.12 @@ -253,47 +253,17 @@ 11.13 * @param path the search path string 11.14 * @return the resulting array of directory and JAR file URLs 11.15 */ 11.16 - private static URL[] pathToURLs(String path) { 11.17 - StringTokenizer st = new StringTokenizer(path, File.pathSeparator); 11.18 - URL[] urls = new URL[st.countTokens()]; 11.19 - int count = 0; 11.20 - while (st.hasMoreTokens()) { 11.21 - URL url = fileToURL(new File(st.nextToken())); 11.22 - if (url != null) { 11.23 - urls[count++] = url; 11.24 + private URL[] pathToURLs(String path) { 11.25 + Set<URL> urls = new LinkedHashSet<URL>(); 11.26 + for (String s: path.split(File.pathSeparator)) { 11.27 + if (s.isEmpty()) continue; 11.28 + try { 11.29 + urls.add(new File(s).getAbsoluteFile().toURI().toURL()); 11.30 + } catch (MalformedURLException e) { 11.31 + message.error("doclet.MalformedURL", s); 11.32 } 11.33 } 11.34 - urls = Arrays.copyOf(urls, count); 11.35 - return urls; 11.36 - } 11.37 - 11.38 - /** 11.39 - * Returns the directory or JAR file URL corresponding to the specified 11.40 - * local file name. 11.41 - * 11.42 - * @param file the File object 11.43 - * @return the resulting directory or JAR file URL, or null if unknown 11.44 - */ 11.45 - private static URL fileToURL(File file) { 11.46 - String name; 11.47 - try { 11.48 - name = file.getCanonicalPath(); 11.49 - } catch (IOException e) { 11.50 - name = file.getAbsolutePath(); 11.51 - } 11.52 - name = name.replace(File.separatorChar, '/'); 11.53 - if (!name.startsWith("/")) { 11.54 - name = "/" + name; 11.55 - } 11.56 - // If the file does not exist, then assume that it's a directory 11.57 - if (!file.isFile()) { 11.58 - name = name + "/"; 11.59 - } 11.60 - try { 11.61 - return new URL("file", "", name); 11.62 - } catch (MalformedURLException e) { 11.63 - throw new IllegalArgumentException("file"); 11.64 - } 11.65 + return urls.toArray(new URL[urls.size()]); 11.66 } 11.67 11.68
12.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 12.2 +++ b/src/share/classes/com/sun/tools/doclets/internal/toolkit/util/DocFile.java Wed Oct 31 13:48:15 2012 -0700 12.3 @@ -0,0 +1,399 @@ 12.4 +/* 12.5 + * Copyright (c) 1998, 2012, Oracle and/or its affiliates. All rights reserved. 12.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 12.7 + * 12.8 + * This code is free software; you can redistribute it and/or modify it 12.9 + * under the terms of the GNU General Public License version 2 only, as 12.10 + * published by the Free Software Foundation. Oracle designates this 12.11 + * particular file as subject to the "Classpath" exception as provided 12.12 + * by Oracle in the LICENSE file that accompanied this code. 12.13 + * 12.14 + * This code is distributed in the hope that it will be useful, but WITHOUT 12.15 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 12.16 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12.17 + * version 2 for more details (a copy is included in the LICENSE file that 12.18 + * accompanied this code). 12.19 + * 12.20 + * You should have received a copy of the GNU General Public License version 12.21 + * 2 along with this work; if not, write to the Free Software Foundation, 12.22 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 12.23 + * 12.24 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 12.25 + * or visit www.oracle.com if you need additional information or have any 12.26 + * questions. 12.27 + */ 12.28 + 12.29 +package com.sun.tools.doclets.internal.toolkit.util; 12.30 + 12.31 +import java.io.BufferedInputStream; 12.32 +import java.io.BufferedOutputStream; 12.33 +import java.io.BufferedReader; 12.34 +import java.io.BufferedWriter; 12.35 +import java.io.File; 12.36 +import java.io.FileInputStream; 12.37 +import java.io.FileNotFoundException; 12.38 +import java.io.FileOutputStream; 12.39 +import java.io.IOException; 12.40 +import java.io.InputStream; 12.41 +import java.io.InputStreamReader; 12.42 +import java.io.OutputStream; 12.43 +import java.io.OutputStreamWriter; 12.44 +import java.io.UnsupportedEncodingException; 12.45 +import java.io.Writer; 12.46 +import java.util.ArrayList; 12.47 +import java.util.LinkedHashSet; 12.48 +import java.util.List; 12.49 +import java.util.Set; 12.50 + 12.51 +import javax.tools.JavaFileManager.Location; 12.52 +import javax.tools.StandardLocation; 12.53 + 12.54 +import com.sun.tools.doclets.internal.toolkit.Configuration; 12.55 + 12.56 +/** 12.57 + * Abstraction for handling files, which may be specified directly 12.58 + * (e.g. via a path on the command line) or relative to a Location. 12.59 + * 12.60 + * <p><b>This is NOT part of any supported API. 12.61 + * If you write code that depends on this, you do so at your own risk. 12.62 + * This code and its internal interfaces are subject to change or 12.63 + * deletion without notice.</b> 12.64 + * 12.65 + * @since 8 12.66 + */ 12.67 +public class DocFile { 12.68 + 12.69 + /** 12.70 + * The doclet configuration. 12.71 + * Provides access to options such as docencoding, output directory, etc. 12.72 + */ 12.73 + private final Configuration configuration; 12.74 + 12.75 + /** 12.76 + * The location for this file. Maybe null if the file was created without 12.77 + * a location or path. 12.78 + */ 12.79 + private final Location location; 12.80 + 12.81 + /** 12.82 + * The path relative to the (output) location. Maybe null if the file was 12.83 + * created without a location or path. 12.84 + */ 12.85 + private final DocPath path; 12.86 + 12.87 + /** 12.88 + * The file object itself. 12.89 + * This is temporary, until we create different subtypes of DocFile. 12.90 + */ 12.91 + private final File file; 12.92 + 12.93 + /** Create a DocFile for a directory. */ 12.94 + public static DocFile createFileForDirectory(Configuration configuration, String file) { 12.95 + return new DocFile(configuration, new File(file)); 12.96 + } 12.97 + 12.98 + /** Create a DocFile for a file that will be opened for reading. */ 12.99 + public static DocFile createFileForInput(Configuration configuration, String file) { 12.100 + return new DocFile(configuration, new File(file)); 12.101 + } 12.102 + 12.103 + /** Create a DocFile for a file that will be opened for writing. */ 12.104 + public static DocFile createFileForOutput(Configuration configuration, DocPath path) { 12.105 + return new DocFile(configuration, StandardLocation.CLASS_OUTPUT, path); 12.106 + } 12.107 + 12.108 + /** 12.109 + * List the directories and files found in subdirectories along the 12.110 + * elements of the given location. 12.111 + * @param configuration the doclet configuration 12.112 + * @param location currently, only {@link StandardLocation#SOURCE_PATH} is supported. 12.113 + * @param path the subdirectory of the directories of the location for which to 12.114 + * list files 12.115 + */ 12.116 + public static Iterable<DocFile> list(Configuration configuration, Location location, DocPath path) { 12.117 + if (location != StandardLocation.SOURCE_PATH) 12.118 + throw new IllegalArgumentException(); 12.119 + 12.120 + Set<DocFile> files = new LinkedHashSet<DocFile>(); 12.121 + for (String s : configuration.sourcepath.split(File.pathSeparator)) { 12.122 + if (s.isEmpty()) 12.123 + continue; 12.124 + File f = new File(s); 12.125 + if (f.isDirectory()) { 12.126 + f = new File(f, path.getPath()); 12.127 + if (f.exists()) 12.128 + files.add(new DocFile(configuration, f)); 12.129 + } 12.130 + } 12.131 + return files; 12.132 + } 12.133 + 12.134 + /** Create a DocFile for a given file. */ 12.135 + private DocFile(Configuration configuration, File file) { 12.136 + this.configuration = configuration; 12.137 + this.location = null; 12.138 + this.path = null; 12.139 + this.file = file; 12.140 + } 12.141 + 12.142 + /** Create a DocFile for a given location and relative path. */ 12.143 + private DocFile(Configuration configuration, Location location, DocPath path) { 12.144 + this.configuration = configuration; 12.145 + this.location = location; 12.146 + this.path = path; 12.147 + this.file = path.resolveAgainst(configuration.destDirName); 12.148 + } 12.149 + 12.150 + /** Open an input stream for the file. */ 12.151 + public InputStream openInputStream() throws FileNotFoundException { 12.152 + return new BufferedInputStream(new FileInputStream(file)); 12.153 + } 12.154 + 12.155 + /** 12.156 + * Open an output stream for the file. 12.157 + * The file must have been created with a location of 12.158 + * {@link StandardLocation#CLASS_OUTPUT} and a corresponding relative path. 12.159 + */ 12.160 + public OutputStream openOutputStream() throws IOException, UnsupportedEncodingException { 12.161 + if (location != StandardLocation.CLASS_OUTPUT) 12.162 + throw new IllegalStateException(); 12.163 + 12.164 + createDirectoryForFile(file); 12.165 + return new BufferedOutputStream(new FileOutputStream(file)); 12.166 + } 12.167 + 12.168 + /** 12.169 + * Open an writer for the file, using the encoding (if any) given in the 12.170 + * doclet configuration. 12.171 + * The file must have been created with a location of 12.172 + * {@link StandardLocation#CLASS_OUTPUT} and a corresponding relative path. 12.173 + */ 12.174 + public Writer openWriter() throws IOException, UnsupportedEncodingException { 12.175 + if (location != StandardLocation.CLASS_OUTPUT) 12.176 + throw new IllegalStateException(); 12.177 + 12.178 + createDirectoryForFile(file); 12.179 + FileOutputStream fos = new FileOutputStream(file); 12.180 + if (configuration.docencoding == null) { 12.181 + return new BufferedWriter(new OutputStreamWriter(fos)); 12.182 + } else { 12.183 + return new BufferedWriter(new OutputStreamWriter(fos, configuration.docencoding)); 12.184 + } 12.185 + } 12.186 + 12.187 + /** 12.188 + * Copy the contents of another file directly to this file. 12.189 + */ 12.190 + public void copyFile(DocFile fromFile) throws IOException { 12.191 + if (location != StandardLocation.CLASS_OUTPUT) 12.192 + throw new IllegalStateException(); 12.193 + 12.194 + createDirectoryForFile(file); 12.195 + 12.196 + InputStream input = fromFile.openInputStream(); 12.197 + OutputStream output = openOutputStream(); 12.198 + try { 12.199 + byte[] bytearr = new byte[1024]; 12.200 + int len; 12.201 + while ((len = input.read(bytearr)) != -1) { 12.202 + output.write(bytearr, 0, len); 12.203 + } 12.204 + } catch (FileNotFoundException exc) { 12.205 + } catch (SecurityException exc) { 12.206 + } finally { 12.207 + input.close(); 12.208 + output.close(); 12.209 + } 12.210 + } 12.211 + 12.212 + /** 12.213 + * Copy the contents of a resource file to this file. 12.214 + * @param resource the path of the resource, relative to the package of this class 12.215 + * @param overwrite whether or not to overwrite the file if it already exists 12.216 + * @param replaceNewLine if false, the file is copied as a binary file; 12.217 + * if true, the file is written line by line, using the platform line 12.218 + * separator 12.219 + */ 12.220 + public void copyResource(DocPath resource, boolean overwrite, boolean replaceNewLine) { 12.221 + if (location != StandardLocation.CLASS_OUTPUT) 12.222 + throw new IllegalStateException(); 12.223 + 12.224 + if (file.exists() && !overwrite) 12.225 + return; 12.226 + 12.227 + createDirectoryForFile(file); 12.228 + 12.229 + try { 12.230 + InputStream in = Configuration.class.getResourceAsStream(resource.getPath()); 12.231 + if (in == null) 12.232 + return; 12.233 + 12.234 + OutputStream out = new FileOutputStream(file); 12.235 + try { 12.236 + if (!replaceNewLine) { 12.237 + byte[] buf = new byte[2048]; 12.238 + int n; 12.239 + while((n = in.read(buf))>0) out.write(buf,0,n); 12.240 + } else { 12.241 + BufferedReader reader = new BufferedReader(new InputStreamReader(in)); 12.242 + BufferedWriter writer; 12.243 + if (configuration.docencoding == null) { 12.244 + writer = new BufferedWriter(new OutputStreamWriter(out)); 12.245 + } else { 12.246 + writer = new BufferedWriter(new OutputStreamWriter(out, 12.247 + configuration.docencoding)); 12.248 + } 12.249 + try { 12.250 + String line; 12.251 + while ((line = reader.readLine()) != null) { 12.252 + writer.write(line); 12.253 + writer.write(DocletConstants.NL); 12.254 + } 12.255 + } finally { 12.256 + reader.close(); 12.257 + writer.close(); 12.258 + } 12.259 + } 12.260 + } finally { 12.261 + in.close(); 12.262 + out.close(); 12.263 + } 12.264 + } catch (IOException e) { 12.265 + e.printStackTrace(System.err); 12.266 + throw new DocletAbortException(); 12.267 + } 12.268 + } 12.269 + 12.270 + /** Return true if the file can be read. */ 12.271 + public boolean canRead() { 12.272 + return file.canRead(); 12.273 + } 12.274 + 12.275 + /** Return true if the file can be written. */ 12.276 + public boolean canWrite() { 12.277 + return file.canRead(); 12.278 + } 12.279 + 12.280 + /** Return true if the file exists. */ 12.281 + public boolean exists() { 12.282 + return file.exists(); 12.283 + } 12.284 + 12.285 + /** Return the base name (last component) of the file name. */ 12.286 + public String getName() { 12.287 + return file.getName(); 12.288 + } 12.289 + 12.290 + /** Return the file system path for this file. */ 12.291 + public String getPath() { 12.292 + return file.getPath(); 12.293 + } 12.294 + 12.295 + /** Return true is file has an absolute path name. */ 12.296 + boolean isAbsolute() { 12.297 + return file.isAbsolute(); 12.298 + } 12.299 + 12.300 + /** Return true is file identifies a directory. */ 12.301 + public boolean isDirectory() { 12.302 + return file.isDirectory(); 12.303 + } 12.304 + 12.305 + /** Return true is file identifies a file. */ 12.306 + public boolean isFile() { 12.307 + return file.isFile(); 12.308 + } 12.309 + 12.310 + /** Return true if this file is the same as another. */ 12.311 + public boolean isSameFile(DocFile other) { 12.312 + try { 12.313 + return file.exists() 12.314 + && file.getCanonicalFile().equals(other.file.getCanonicalFile()); 12.315 + } catch (IOException e) { 12.316 + return false; 12.317 + } 12.318 + } 12.319 + 12.320 + /** If the file is a directory, list its contents. */ 12.321 + public Iterable<DocFile> list() { 12.322 + List<DocFile> files = new ArrayList<DocFile>(); 12.323 + for (File f: file.listFiles()) { 12.324 + files.add(new DocFile(configuration, f)); 12.325 + } 12.326 + return files; 12.327 + } 12.328 + 12.329 + /** Create the file as a directory, including any parent directories. */ 12.330 + public boolean mkdirs() { 12.331 + return file.mkdirs(); 12.332 + } 12.333 + 12.334 + /** 12.335 + * Derive a new file by resolving a relative path against this file. 12.336 + * The new file will inherit the configuration and location of this file 12.337 + * If this file has a path set, the new file will have a corresponding 12.338 + * new path. 12.339 + */ 12.340 + public DocFile resolve(DocPath p) { 12.341 + return resolve(p.getPath()); 12.342 + } 12.343 + 12.344 + /** 12.345 + * Derive a new file by resolving a relative path against this file. 12.346 + * The new file will inherit the configuration and location of this file 12.347 + * If this file has a path set, the new file will have a corresponding 12.348 + * new path. 12.349 + */ 12.350 + public DocFile resolve(String p) { 12.351 + if (location == null && path == null) { 12.352 + return new DocFile(configuration, new File(file, p)); 12.353 + } else { 12.354 + return new DocFile(configuration, location, path.resolve(p)); 12.355 + } 12.356 + } 12.357 + 12.358 + /** 12.359 + * Resolve a relative file against the given output location. 12.360 + * @param locn Currently, only SOURCE_OUTPUT is supported. 12.361 + */ 12.362 + public DocFile resolveAgainst(StandardLocation locn) { 12.363 + if (locn != StandardLocation.CLASS_OUTPUT) 12.364 + throw new IllegalArgumentException(); 12.365 + return new DocFile(configuration, 12.366 + new File(configuration.destDirName, file.getPath())); 12.367 + } 12.368 + 12.369 + /** 12.370 + * Given a path string create all the directories in the path. For example, 12.371 + * if the path string is "java/applet", the method will create directory 12.372 + * "java" and then "java/applet" if they don't exist. The file separator 12.373 + * string "/" is platform dependent system property. 12.374 + * 12.375 + * @param path Directory path string. 12.376 + */ 12.377 + private void createDirectoryForFile(File file) { 12.378 + File dir = file.getParentFile(); 12.379 + if (dir == null || dir.exists() || dir.mkdirs()) 12.380 + return; 12.381 + 12.382 + configuration.message.error( 12.383 + "doclet.Unable_to_create_directory_0", dir.getPath()); 12.384 + throw new DocletAbortException(); 12.385 + } 12.386 + 12.387 + /** Return a string to identify the contents of this object, 12.388 + * for debugging purposes. 12.389 + */ 12.390 + @Override 12.391 + public String toString() { 12.392 + StringBuilder sb = new StringBuilder(); 12.393 + sb.append("DocFile["); 12.394 + if (location != null) 12.395 + sb.append("locn:").append(location).append(","); 12.396 + if (path != null) 12.397 + sb.append("path:").append(path.getPath()).append(","); 12.398 + sb.append("file:").append(file); 12.399 + sb.append("]"); 12.400 + return sb.toString(); 12.401 + } 12.402 +}
13.1 --- a/src/share/classes/com/sun/tools/doclets/internal/toolkit/util/DocPaths.java Wed Oct 31 08:31:40 2012 -0700 13.2 +++ b/src/share/classes/com/sun/tools/doclets/internal/toolkit/util/DocPaths.java Wed Oct 31 13:48:15 2012 -0700 13.3 @@ -28,6 +28,11 @@ 13.4 /** 13.5 * Standard DocPath objects. 13.6 * 13.7 + * <p><b>This is NOT part of any supported API. 13.8 + * If you write code that depends on this, you do so at your own risk. 13.9 + * This code and its internal interfaces are subject to change or 13.10 + * deletion without notice.</b> 13.11 + * 13.12 * @since 8 13.13 */ 13.14 public class DocPaths {
14.1 --- a/src/share/classes/com/sun/tools/doclets/internal/toolkit/util/Extern.java Wed Oct 31 08:31:40 2012 -0700 14.2 +++ b/src/share/classes/com/sun/tools/doclets/internal/toolkit/util/Extern.java Wed Oct 31 13:48:15 2012 -0700 14.3 @@ -30,6 +30,8 @@ 14.4 import java.util.HashMap; 14.5 import java.util.Map; 14.6 14.7 +import javax.tools.StandardLocation; 14.8 + 14.9 import com.sun.javadoc.*; 14.10 import com.sun.tools.doclets.internal.toolkit.*; 14.11 14.12 @@ -177,7 +179,7 @@ 14.13 if (isUrl(pkglisturl)) { 14.14 readPackageListFromURL(url, toURL(pkglisturl)); 14.15 } else { 14.16 - readPackageListFromFile(url, new File(pkglisturl)); 14.17 + readPackageListFromFile(url, DocFile.createFileForInput(configuration, pkglisturl)); 14.18 } 14.19 return true; 14.20 } catch (Fault f) { 14.21 @@ -247,16 +249,18 @@ 14.22 * @param path URL or directory path to the packages. 14.23 * @param pkgListPath Path to the local "package-list" file. 14.24 */ 14.25 - private void readPackageListFromFile(String path, File pkgListPath) 14.26 + private void readPackageListFromFile(String path, DocFile pkgListPath) 14.27 throws Fault { 14.28 - File file = new File(pkgListPath, "package-list"); 14.29 + DocFile file = pkgListPath.resolve(DocPaths.PACKAGE_LIST); 14.30 if (! (file.isAbsolute() || linkoffline)){ 14.31 - file = new File(configuration.destDirName, file.getPath()); 14.32 + file = file.resolveAgainst(StandardLocation.CLASS_OUTPUT); 14.33 } 14.34 try { 14.35 if (file.exists() && file.canRead()) { 14.36 - readPackageList(new FileInputStream(file), path, 14.37 - ! ((new File(path)).isAbsolute() || isUrl(path))); 14.38 + boolean pathIsRelative = 14.39 + !DocFile.createFileForInput(configuration, path).isAbsolute() 14.40 + && !isUrl(path); 14.41 + readPackageList(file.openInputStream(), path, pathIsRelative); 14.42 } else { 14.43 throw new Fault(configuration.getText("doclet.File_error", file.getPath()), null); 14.44 }
15.1 --- a/src/share/classes/com/sun/tools/doclets/internal/toolkit/util/PackageListWriter.java Wed Oct 31 08:31:40 2012 -0700 15.2 +++ b/src/share/classes/com/sun/tools/doclets/internal/toolkit/util/PackageListWriter.java Wed Oct 31 13:48:15 2012 -0700 15.3 @@ -52,7 +52,7 @@ 15.4 * @param configuration the current configuration of the doclet. 15.5 */ 15.6 public PackageListWriter(Configuration configuration) throws IOException { 15.7 - super(Util.genWriter(configuration, DocPaths.PACKAGE_LIST)); 15.8 + super(DocFile.createFileForOutput(configuration, DocPaths.PACKAGE_LIST).openWriter()); 15.9 this.configuration = configuration; 15.10 } 15.11
16.1 --- a/src/share/classes/com/sun/tools/doclets/internal/toolkit/util/SourcePath.java Wed Oct 31 08:31:40 2012 -0700 16.2 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 16.3 @@ -1,132 +0,0 @@ 16.4 -/* 16.5 - * Copyright (c) 1998, 2012, Oracle and/or its affiliates. All rights reserved. 16.6 - * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 16.7 - * 16.8 - * This code is free software; you can redistribute it and/or modify it 16.9 - * under the terms of the GNU General Public License version 2 only, as 16.10 - * published by the Free Software Foundation. Oracle designates this 16.11 - * particular file as subject to the "Classpath" exception as provided 16.12 - * by Oracle in the LICENSE file that accompanied this code. 16.13 - * 16.14 - * This code is distributed in the hope that it will be useful, but WITHOUT 16.15 - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 16.16 - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 16.17 - * version 2 for more details (a copy is included in the LICENSE file that 16.18 - * accompanied this code). 16.19 - * 16.20 - * You should have received a copy of the GNU General Public License version 16.21 - * 2 along with this work; if not, write to the Free Software Foundation, 16.22 - * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 16.23 - * 16.24 - * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 16.25 - * or visit www.oracle.com if you need additional information or have any 16.26 - * questions. 16.27 - */ 16.28 - 16.29 -package com.sun.tools.doclets.internal.toolkit.util; 16.30 - 16.31 -import java.io.File; 16.32 - 16.33 -/** 16.34 - * This class is used to represent a source path which can contain only 16.35 - * directories no zip files. If a zip file is specified in the command line it 16.36 - * will not get reflected in the SourcePath. 16.37 - * 16.38 - * This code is not part of an API. 16.39 - * It is implementation that is subject to change. 16.40 - * Do not use it as an API 16.41 - * 16.42 - * @author Atul M Dambalkar 16.43 - */ 16.44 -public class SourcePath { 16.45 - private final char dirSeparator = File.pathSeparatorChar; 16.46 - 16.47 - /** 16.48 - * The original class path string 16.49 - */ 16.50 - private String pathstr; 16.51 - 16.52 - /** 16.53 - * List of source path entries. Each entry is a directory. 16.54 - */ 16.55 - private File[] sourcePath; 16.56 - 16.57 - 16.58 - /** 16.59 - * Build a source path from the specified path string on the command line. 16.60 - */ 16.61 - public SourcePath(String pathstr) { 16.62 - init(pathstr); 16.63 - } 16.64 - 16.65 - /** 16.66 - * Build a default source path from the path strings specified by 16.67 - * the properties env.class.path. 16.68 - */ 16.69 - public SourcePath() { 16.70 - init(System.getProperty("env.class.path")); 16.71 - } 16.72 - 16.73 - /** 16.74 - * Initialize the SourcePath File array, which will contain only the 16.75 - * directory names from the given path string. 16.76 - * 16.77 - * @param pathstr Path String. 16.78 - */ 16.79 - private void init(String pathstr) { 16.80 - if (pathstr == null || pathstr.length() == 0) { 16.81 - pathstr = "."; 16.82 - } 16.83 - 16.84 - int noOfFileSep = 0; 16.85 - int index = 0; 16.86 - this.pathstr = pathstr; // Save original class path string 16.87 - 16.88 - // Count the number of path separators 16.89 - while ((index = pathstr.indexOf(dirSeparator, index)) != -1) { 16.90 - noOfFileSep++; 16.91 - index++; 16.92 - } 16.93 - // Build the source path 16.94 - File[] tempPath = new File[noOfFileSep + 1]; 16.95 - int tempPathIndex = 0; 16.96 - int len = pathstr.length(); 16.97 - int sepPos = 0; 16.98 - for (index = 0; index < len; index = sepPos + 1) { 16.99 - sepPos = pathstr.indexOf(dirSeparator, index); 16.100 - if (sepPos < 0) { 16.101 - sepPos = len; 16.102 - } 16.103 - File file = new File(pathstr.substring(index, sepPos)); 16.104 - if (file.isDirectory()) { 16.105 - tempPath[tempPathIndex++] = file; 16.106 - } // if it is really a file, ignore it. 16.107 - } 16.108 - sourcePath = new File[tempPathIndex]; 16.109 - System.arraycopy((Object)tempPath, 0, (Object)sourcePath, 16.110 - 0, tempPathIndex); 16.111 - } 16.112 - 16.113 - /** 16.114 - * Find the specified directory in the source path. 16.115 - * 16.116 - * @param p Name of the directory to be searched for in the source path. 16.117 - * @return File Return the directory if found else return null. 16.118 - */ 16.119 - public File getDirectory(DocPath p) { 16.120 - for (int i = 0; i < sourcePath.length; i++) { 16.121 - File directoryNeeded = new File(sourcePath[i], p.getPath()); 16.122 - if (directoryNeeded.isDirectory()) { 16.123 - return directoryNeeded; 16.124 - } 16.125 - } 16.126 - return null; 16.127 - } 16.128 - 16.129 - /** 16.130 - * Return original source path string. 16.131 - */ 16.132 - public String toString() { 16.133 - return pathstr; 16.134 - } 16.135 -}
17.1 --- a/src/share/classes/com/sun/tools/doclets/internal/toolkit/util/Util.java Wed Oct 31 08:31:40 2012 -0700 17.2 +++ b/src/share/classes/com/sun/tools/doclets/internal/toolkit/util/Util.java Wed Oct 31 13:48:15 2012 -0700 17.3 @@ -30,6 +30,7 @@ 17.4 17.5 import com.sun.javadoc.*; 17.6 import com.sun.tools.doclets.internal.toolkit.*; 17.7 +import javax.tools.StandardLocation; 17.8 17.9 /** 17.10 * Utilities Class for Doclets. 17.11 @@ -192,32 +193,6 @@ 17.12 } 17.13 17.14 /** 17.15 - * Copy source file to destination file. 17.16 - * 17.17 - * @throws SecurityException 17.18 - * @throws IOException 17.19 - */ 17.20 - public static void copyFile(File destfile, File srcfile) 17.21 - throws IOException { 17.22 - byte[] bytearr = new byte[512]; 17.23 - int len = 0; 17.24 - FileInputStream input = new FileInputStream(srcfile); 17.25 - File destDir = destfile.getParentFile(); 17.26 - destDir.mkdirs(); 17.27 - FileOutputStream output = new FileOutputStream(destfile); 17.28 - try { 17.29 - while ((len = input.read(bytearr)) != -1) { 17.30 - output.write(bytearr, 0, len); 17.31 - } 17.32 - } catch (FileNotFoundException exc) { 17.33 - } catch (SecurityException exc) { 17.34 - } finally { 17.35 - input.close(); 17.36 - output.close(); 17.37 - } 17.38 - } 17.39 - 17.40 - /** 17.41 * Copy the given directory contents from the source package directory 17.42 * to the generated documentation directory. For example for a package 17.43 * java.lang this method find out the source location of the package using 17.44 @@ -230,38 +205,45 @@ 17.45 * @param dir The original directory name to copy from. 17.46 * @param overwrite Overwrite files if true. 17.47 */ 17.48 - public static void copyDocFiles(Configuration configuration, 17.49 - File path, DocPath dir, boolean overwrite) { 17.50 - if (checkCopyDocFilesErrors(configuration, path, dir)) { 17.51 - return; 17.52 - } 17.53 - File srcdir = new File(path, dir.getPath()); 17.54 - File destdir = new File(configuration.docFileDestDirName, dir.getPath()); 17.55 + public static void copyDocFiles(Configuration configuration, PackageDoc pd) { 17.56 + copyDocFiles(configuration, DocPath.forPackage(pd).resolve(DocPaths.DOC_FILES)); 17.57 + } 17.58 + 17.59 + public static void copyDocFiles(Configuration configuration, DocPath dir) { 17.60 try { 17.61 - createDirectory(configuration, destdir); 17.62 - String[] files = srcdir.list(); 17.63 - for (int i = 0; i < files.length; i++) { 17.64 - File srcfile = new File(srcdir, files[i]); 17.65 - File destfile = new File(destdir, files[i]); 17.66 - if (srcfile.isFile()) { 17.67 - if (destfile.exists() && ! overwrite) { 17.68 - configuration.message.warning((SourcePosition) null, 17.69 - "doclet.Copy_Overwrite_warning", 17.70 - srcfile.toString(), destdir.toString()); 17.71 - } else { 17.72 - configuration.message.notice( 17.73 - "doclet.Copying_File_0_To_Dir_1", 17.74 - srcfile.toString(), destdir.toString()); 17.75 - Util.copyFile(destfile, srcfile); 17.76 - } 17.77 - } else if (srcfile.isDirectory()) { 17.78 - if (configuration.copydocfilesubdirs 17.79 - && ! configuration.shouldExcludeDocFileDir( 17.80 - srcfile.getName())){ 17.81 - copyDocFiles(configuration, path, dir.resolve(files[i]), 17.82 - overwrite); 17.83 + boolean first = true; 17.84 + for (DocFile f : DocFile.list(configuration, StandardLocation.SOURCE_PATH, dir)) { 17.85 + if (!f.isDirectory()) { 17.86 + continue; 17.87 + } 17.88 + DocFile srcdir = f; 17.89 + DocFile destdir = DocFile.createFileForOutput(configuration, dir); 17.90 + if (srcdir.isSameFile(destdir)) { 17.91 + continue; 17.92 + } 17.93 + 17.94 + for (DocFile srcfile: srcdir.list()) { 17.95 + DocFile destfile = destdir.resolve(srcfile.getName()); 17.96 + if (srcfile.isFile()) { 17.97 + if (destfile.exists() && !first) { 17.98 + configuration.message.warning((SourcePosition) null, 17.99 + "doclet.Copy_Overwrite_warning", 17.100 + srcfile.getPath(), destdir.getPath()); 17.101 + } else { 17.102 + configuration.message.notice( 17.103 + "doclet.Copying_File_0_To_Dir_1", 17.104 + srcfile.getPath(), destdir.getPath()); 17.105 + destfile.copyFile(srcfile); 17.106 + } 17.107 + } else if (srcfile.isDirectory()) { 17.108 + if (configuration.copydocfilesubdirs 17.109 + && !configuration.shouldExcludeDocFileDir(srcfile.getName())) { 17.110 + copyDocFiles(configuration, dir.resolve(srcfile.getName())); 17.111 + } 17.112 } 17.113 } 17.114 + 17.115 + first = false; 17.116 } 17.117 } catch (SecurityException exc) { 17.118 throw new DocletAbortException(); 17.119 @@ -271,170 +253,6 @@ 17.120 } 17.121 17.122 /** 17.123 - * Given the parameters for copying doc-files, check for errors. 17.124 - * 17.125 - * @param configuration The configuration of the current doclet. 17.126 - * @param path The relative path to the directory to be copied. 17.127 - * @param dirName The original directory name to copy from. 17.128 - */ 17.129 - private static boolean checkCopyDocFilesErrors (Configuration configuration, 17.130 - File path, DocPath dirName) { 17.131 - if ((configuration.sourcepath == null || configuration.sourcepath.length() == 0) && 17.132 - (configuration.destDirName == null || configuration.destDirName.length() == 0)) { 17.133 - //The destination path and source path are definitely equal. 17.134 - return true; 17.135 - } 17.136 - File sourcePath, destPath = new File(configuration.destDirName); 17.137 - StringTokenizer pathTokens = new StringTokenizer( 17.138 - configuration.sourcepath == null ? "" : configuration.sourcepath, 17.139 - File.pathSeparator); 17.140 - //Check if the destination path is equal to the source path. If yes, 17.141 - //do not copy doc-file directories. 17.142 - while(pathTokens.hasMoreTokens()){ 17.143 - sourcePath = new File(pathTokens.nextToken()); 17.144 - if(destPath.equals(sourcePath)){ 17.145 - return true; 17.146 - } 17.147 - } 17.148 - //Make sure the doc-file being copied exists. 17.149 - File srcdir = new File(path, dirName.getPath()); 17.150 - if (! srcdir.exists()) { 17.151 - return true; 17.152 - } 17.153 - return false; 17.154 - } 17.155 - 17.156 - /** 17.157 - * Copy a file in the resources directory to the destination 17.158 - * directory (if it is not there already). If 17.159 - * <code>overwrite</code> is true and the destination file 17.160 - * already exists, overwrite it. 17.161 - * 17.162 - * @param configuration Holds the destination directory and error message 17.163 - * @param resourcefile The name of the resource file to copy 17.164 - * @param overwrite A flag to indicate whether the file in the 17.165 - * destination directory will be overwritten if 17.166 - * it already exists. 17.167 - */ 17.168 - public static void copyResourceFile(Configuration configuration, 17.169 - String resourcefile, boolean overwrite) { 17.170 - copyFile(configuration, resourcefile, DocPaths.RESOURCES, DocPaths.RESOURCES, 17.171 - overwrite, false); 17.172 - } 17.173 - 17.174 - /** 17.175 - * Copy a file from a source directory to a destination directory 17.176 - * (if it is not there already). If <code>overwrite</code> is true and 17.177 - * the destination file already exists, overwrite it. 17.178 - * 17.179 - * @param configuration Holds the error message 17.180 - * @param file The name of the file to copy 17.181 - * @param source The source directory 17.182 - * @param destination The destination directory where the file needs to be copied 17.183 - * @param overwrite A flag to indicate whether the file in the 17.184 - * destination directory will be overwritten if 17.185 - * it already exists. 17.186 - * @param replaceNewLine true if the newline needs to be replaced with platform- 17.187 - * specific newline. 17.188 - */ 17.189 - public static void copyFile(Configuration configuration, String file, DocPath source, 17.190 - DocPath destination, boolean overwrite, boolean replaceNewLine) { 17.191 - copyFile(configuration, file, source.getPath(), destination.getPath(), 17.192 - overwrite, replaceNewLine); 17.193 - } 17.194 - 17.195 - public static void copyFile(Configuration configuration, String file, String source, 17.196 - String destination, boolean overwrite, boolean replaceNewLine) { 17.197 - File destdir = configuration.destDirName.isEmpty() ? 17.198 - (destination.isEmpty() ? null : new File(destination)) : 17.199 - new File(configuration.destDirName, destination); 17.200 - File destfile = (destdir == null) ? new File(file) : new File(destdir, file); 17.201 - createDirectory(configuration, destfile.getParentFile()); 17.202 - if (destfile.exists() && (! overwrite)) return; 17.203 - try { 17.204 - InputStream in = Configuration.class.getResourceAsStream( 17.205 - source + '/' + file); 17.206 - if (in == null) return; 17.207 - OutputStream out = new FileOutputStream(destfile); 17.208 - try { 17.209 - if (!replaceNewLine) { 17.210 - byte[] buf = new byte[2048]; 17.211 - int n; 17.212 - while((n = in.read(buf))>0) out.write(buf,0,n); 17.213 - } else { 17.214 - BufferedReader reader = new BufferedReader(new InputStreamReader(in)); 17.215 - BufferedWriter writer; 17.216 - if (configuration.docencoding == null) { 17.217 - writer = new BufferedWriter(new OutputStreamWriter(out)); 17.218 - } else { 17.219 - writer = new BufferedWriter(new OutputStreamWriter(out, 17.220 - configuration.docencoding)); 17.221 - } 17.222 - try { 17.223 - String line; 17.224 - while ((line = reader.readLine()) != null) { 17.225 - writer.write(line); 17.226 - writer.write(DocletConstants.NL); 17.227 - } 17.228 - } finally { 17.229 - reader.close(); 17.230 - writer.close(); 17.231 - } 17.232 - } 17.233 - } finally { 17.234 - in.close(); 17.235 - out.close(); 17.236 - } 17.237 - } catch (IOException ie) { 17.238 - ie.printStackTrace(System.err); 17.239 - throw new DocletAbortException(); 17.240 - } 17.241 - } 17.242 - 17.243 - /** 17.244 - * Given a path string create all the directories in the path. For example, 17.245 - * if the path string is "java/applet", the method will create directory 17.246 - * "java" and then "java/applet" if they don't exist. The file separator 17.247 - * string "/" is platform dependent system property. 17.248 - * 17.249 - * @param dir Directory path string. 17.250 - */ 17.251 - public static void createDirectory(Configuration configuration, File dir) { 17.252 - if (dir == null) { 17.253 - return; 17.254 - } 17.255 - if (dir.exists()) { 17.256 - return; 17.257 - } else { 17.258 - if (dir.mkdirs()) { 17.259 - return; 17.260 - } else { 17.261 - configuration.message.error( 17.262 - "doclet.Unable_to_create_directory_0", dir.getPath()); 17.263 - throw new DocletAbortException(); 17.264 - } 17.265 - } 17.266 - } 17.267 - 17.268 - /** 17.269 - * Given a PackageDoc, return the source path for that package. 17.270 - * @param configuration The Configuration for the current Doclet. 17.271 - * @param pkgDoc The package to search the path for. 17.272 - * @return A string representing the path to the given package. 17.273 - */ 17.274 - public static File getPackageSourcePath(Configuration configuration, 17.275 - PackageDoc pkgDoc) { 17.276 - DocPath pkgPath = DocPath.forPackage(pkgDoc); 17.277 - File pkgDir = new SourcePath(configuration.sourcepath).getDirectory(pkgPath); 17.278 - if (pkgDir == null) 17.279 - return null; 17.280 - //Make sure that both paths are using the same separators. 17.281 - String completePath = Util.replaceText(pkgDir.getPath(), File.separator, "/"); 17.282 - String pathForPkg = completePath.substring(0, completePath.lastIndexOf(pkgPath.getPath())); 17.283 - return new File(pathForPkg); 17.284 - } 17.285 - 17.286 - /** 17.287 * We want the list of types in alphabetical order. However, types are not 17.288 * comparable. We need a comparator for now. 17.289 */ 17.290 @@ -639,31 +457,6 @@ 17.291 } 17.292 17.293 /** 17.294 - * Create the directory path for the file to be generated, construct 17.295 - * FileOutputStream and OutputStreamWriter depending upon docencoding. 17.296 - * 17.297 - * @param path The directory path to be created for this file. 17.298 - * @exception IOException Exception raised by the FileWriter is passed on 17.299 - * to next level. 17.300 - * @exception UnsupportedEncodingException Exception raised by the 17.301 - * OutputStreamWriter is passed on to next level. 17.302 - * @return Writer Writer for the file getting generated. 17.303 - * @see java.io.FileOutputStream 17.304 - * @see java.io.OutputStreamWriter 17.305 - */ 17.306 - public static Writer genWriter(Configuration configuration, DocPath path) 17.307 - throws IOException, UnsupportedEncodingException { 17.308 - File file = path.resolveAgainst(configuration.destDirName); 17.309 - createDirectory(configuration, file.getParentFile()); 17.310 - FileOutputStream fos = new FileOutputStream(file); 17.311 - if (configuration.docencoding == null) { 17.312 - return new BufferedWriter(new OutputStreamWriter(fos)); 17.313 - } else { 17.314 - return new BufferedWriter(new OutputStreamWriter(fos, configuration.docencoding)); 17.315 - } 17.316 - } 17.317 - 17.318 - /** 17.319 * Given an annotation, return true if it should be documented and false 17.320 * otherwise. 17.321 * 17.322 @@ -683,47 +476,6 @@ 17.323 } 17.324 17.325 /** 17.326 - * Given a string, return an array of tokens. The separator can be escaped 17.327 - * with the '\' character. The '\' character may also be escaped by the 17.328 - * '\' character. 17.329 - * 17.330 - * @param s the string to tokenize. 17.331 - * @param separator the separator char. 17.332 - * @param maxTokens the maxmimum number of tokens returned. If the 17.333 - * max is reached, the remaining part of s is appended 17.334 - * to the end of the last token. 17.335 - * 17.336 - * @return an array of tokens. 17.337 - */ 17.338 - public static String[] tokenize(String s, char separator, int maxTokens) { 17.339 - List<String> tokens = new ArrayList<String>(); 17.340 - StringBuilder token = new StringBuilder (); 17.341 - boolean prevIsEscapeChar = false; 17.342 - for (int i = 0; i < s.length(); i += Character.charCount(i)) { 17.343 - int currentChar = s.codePointAt(i); 17.344 - if (prevIsEscapeChar) { 17.345 - // Case 1: escaped character 17.346 - token.appendCodePoint(currentChar); 17.347 - prevIsEscapeChar = false; 17.348 - } else if (currentChar == separator && tokens.size() < maxTokens-1) { 17.349 - // Case 2: separator 17.350 - tokens.add(token.toString()); 17.351 - token = new StringBuilder(); 17.352 - } else if (currentChar == '\\') { 17.353 - // Case 3: escape character 17.354 - prevIsEscapeChar = true; 17.355 - } else { 17.356 - // Case 4: regular character 17.357 - token.appendCodePoint(currentChar); 17.358 - } 17.359 - } 17.360 - if (token.length() > 0) { 17.361 - tokens.add(token.toString()); 17.362 - } 17.363 - return tokens.toArray(new String[] {}); 17.364 - } 17.365 - 17.366 - /** 17.367 * Return true if this class is linkable and false if we can't link to the 17.368 * desired class. 17.369 * <br>
18.1 --- a/test/com/sun/javadoc/testDocFileDir/TestDocFileDir.java Wed Oct 31 08:31:40 2012 -0700 18.2 +++ b/test/com/sun/javadoc/testDocFileDir/TestDocFileDir.java Wed Oct 31 13:48:15 2012 -0700 18.3 @@ -1,5 +1,5 @@ 18.4 /* 18.5 - * Copyright (c) 2002, 2004, Oracle and/or its affiliates. All rights reserved. 18.6 + * Copyright (c) 2002, 2012, Oracle and/or its affiliates. All rights reserved. 18.7 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 18.8 * 18.9 * This code is free software; you can redistribute it and/or modify it 18.10 @@ -77,17 +77,19 @@ 18.11 //Output dir = Input Dir 18.12 private static final String[] ARGS1 = 18.13 new String[] { 18.14 - "-d", BUG_ID + "-1", "-sourcepath", 18.15 - "blah" + String.valueOf(File.pathSeparatorChar) + 18.16 - BUG_ID + "-1" + String.valueOf(File.pathSeparatorChar) + 18.17 - "blah", "pkg"}; 18.18 + "-d", BUG_ID + "-1", 18.19 + "-sourcepath", 18.20 + "blah" + File.pathSeparator + BUG_ID + "-1" + File.pathSeparator + "blah", 18.21 + "pkg"}; 18.22 18.23 //Exercising -docfilessubdirs and -excludedocfilessubdir 18.24 private static final String[] ARGS2 = 18.25 new String[] { 18.26 - "-d", BUG_ID + "-2", "-sourcepath", SRC_DIR, 18.27 - "-docfilessubdirs", "-excludedocfilessubdir", 18.28 - "subdir-excluded1:subdir-excluded2", "pkg"}; 18.29 + "-d", BUG_ID + "-2", 18.30 + "-sourcepath", SRC_DIR, 18.31 + "-docfilessubdirs", 18.32 + "-excludedocfilessubdir", "subdir-excluded1:subdir-excluded2", 18.33 + "pkg"}; 18.34 18.35 //Output dir = "", Input dir = "" 18.36 private static final String[] ARGS0 =