src/share/classes/com/sun/tools/javac/file/RegularFileObject.java

Thu, 19 Sep 2013 17:05:32 +0400

author
kizune
date
Thu, 19 Sep 2013 17:05:32 +0400
changeset 2037
36e342dd57e2
parent 1080
edd7d9bd32dd
child 2227
998b10c43157
permissions
-rw-r--r--

8017248: Compiler Diacritics Issue
Reviewed-by: naoto

     1 /*
     2  * Copyright (c) 2005, 2011, Oracle and/or its affiliates. All rights reserved.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     4  *
     5  * This code is free software; you can redistribute it and/or modify it
     6  * under the terms of the GNU General Public License version 2 only, as
     7  * published by the Free Software Foundation.  Oracle designates this
     8  * particular file as subject to the "Classpath" exception as provided
     9  * by Oracle in the LICENSE file that accompanied this code.
    10  *
    11  * This code is distributed in the hope that it will be useful, but WITHOUT
    12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
    13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
    14  * version 2 for more details (a copy is included in the LICENSE file that
    15  * accompanied this code).
    16  *
    17  * You should have received a copy of the GNU General Public License version
    18  * 2 along with this work; if not, write to the Free Software Foundation,
    19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
    20  *
    21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
    22  * or visit www.oracle.com if you need additional information or have any
    23  * questions.
    24  */
    26 package com.sun.tools.javac.file;
    28 import java.io.File;
    29 import java.io.FileInputStream;
    30 import java.io.FileOutputStream;
    31 import java.io.IOException;
    32 import java.io.InputStream;
    33 import java.io.OutputStream;
    34 import java.io.OutputStreamWriter;
    35 import java.io.Writer;
    36 import java.lang.ref.Reference;
    37 import java.lang.ref.SoftReference;
    38 import java.net.URI;
    39 import java.nio.ByteBuffer;
    40 import java.nio.CharBuffer;
    41 import java.nio.charset.CharsetDecoder;
    42 import javax.tools.JavaFileObject;
    43 import java.text.Normalizer;
    45 /**
    46  * A subclass of JavaFileObject representing regular files.
    47  *
    48  * <p><b>This is NOT part of any supported API.
    49  * If you write code that depends on this, you do so at your own risk.
    50  * This code and its internal interfaces are subject to change or
    51  * deletion without notice.</b>
    52  */
    53 class RegularFileObject extends BaseFileObject {
    55     /** Have the parent directories been created?
    56      */
    57     private boolean hasParents = false;
    58     private String name;
    59     final File file;
    60     private Reference<File> absFileRef;
    61     final static boolean isMacOS = System.getProperty("os.name", "").contains("OS X");
    63     public RegularFileObject(JavacFileManager fileManager, File f) {
    64         this(fileManager, f.getName(), f);
    65     }
    67     public RegularFileObject(JavacFileManager fileManager, String name, File f) {
    68         super(fileManager);
    69         if (f.isDirectory()) {
    70             throw new IllegalArgumentException("directories not supported");
    71         }
    72         this.name = name;
    73         this.file = f;
    74     }
    76     @Override
    77     public URI toUri() {
    78         return file.toURI().normalize();
    79     }
    81     @Override
    82     public String getName() {
    83         return file.getPath();
    84     }
    86     @Override
    87     public String getShortName() {
    88         return name;
    89     }
    91     @Override
    92     public JavaFileObject.Kind getKind() {
    93         return getKind(name);
    94     }
    96     @Override
    97     public InputStream openInputStream() throws IOException {
    98         return new FileInputStream(file);
    99     }
   101     @Override
   102     public OutputStream openOutputStream() throws IOException {
   103         fileManager.flushCache(this);
   104         ensureParentDirectoriesExist();
   105         return new FileOutputStream(file);
   106     }
   108     @Override
   109     public CharBuffer getCharContent(boolean ignoreEncodingErrors) throws IOException {
   110         CharBuffer cb = fileManager.getCachedContent(this);
   111         if (cb == null) {
   112             InputStream in = new FileInputStream(file);
   113             try {
   114                 ByteBuffer bb = fileManager.makeByteBuffer(in);
   115                 JavaFileObject prev = fileManager.log.useSource(this);
   116                 try {
   117                     cb = fileManager.decode(bb, ignoreEncodingErrors);
   118                 } finally {
   119                     fileManager.log.useSource(prev);
   120                 }
   121                 fileManager.recycleByteBuffer(bb);
   122                 if (!ignoreEncodingErrors) {
   123                     fileManager.cache(this, cb);
   124                 }
   125             } finally {
   126                 in.close();
   127             }
   128         }
   129         return cb;
   130     }
   132     @Override
   133     public Writer openWriter() throws IOException {
   134         fileManager.flushCache(this);
   135         ensureParentDirectoriesExist();
   136         return new OutputStreamWriter(new FileOutputStream(file), fileManager.getEncodingName());
   137     }
   139     @Override
   140     public long getLastModified() {
   141         return file.lastModified();
   142     }
   144     @Override
   145     public boolean delete() {
   146         return file.delete();
   147     }
   149     @Override
   150     protected CharsetDecoder getDecoder(boolean ignoreEncodingErrors) {
   151         return fileManager.getDecoder(fileManager.getEncodingName(), ignoreEncodingErrors);
   152     }
   154     @Override
   155     protected String inferBinaryName(Iterable<? extends File> path) {
   156         String fPath = file.getPath();
   157         //System.err.println("RegularFileObject " + file + " " +r.getPath());
   158         for (File dir: path) {
   159             //System.err.println("dir: " + dir);
   160             String dPath = dir.getPath();
   161             if (dPath.length() == 0)
   162                 dPath = System.getProperty("user.dir");
   163             if (!dPath.endsWith(File.separator))
   164                 dPath += File.separator;
   165             if (fPath.regionMatches(true, 0, dPath, 0, dPath.length())
   166                 && new File(fPath.substring(0, dPath.length())).equals(new File(dPath))) {
   167                 String relativeName = fPath.substring(dPath.length());
   168                 return removeExtension(relativeName).replace(File.separatorChar, '.');
   169             }
   170         }
   171         return null;
   172     }
   174     @Override
   175     public boolean isNameCompatible(String cn, JavaFileObject.Kind kind) {
   176         cn.getClass();
   177         // null check
   178         if (kind == Kind.OTHER && getKind() != kind) {
   179             return false;
   180         }
   181         String n = cn + kind.extension;
   182         if (name.equals(n)) {
   183             return true;
   184         }
   185         if (isMacOS && Normalizer.isNormalized(name, Normalizer.Form.NFD)
   186             && Normalizer.isNormalized(n, Normalizer.Form.NFC)) {
   187             // On Mac OS X it is quite possible to file name and class
   188             // name normalized in a different way - in that case we have to normalize file name
   189             // to the Normal Form Compised (NFC)
   190             String normName = Normalizer.normalize(name, Normalizer.Form.NFC);
   191             if (normName.equals(n)) {
   192                 this.name = normName;
   193                 return true;
   194             }
   195         }
   197             if (name.equalsIgnoreCase(n)) {
   198             try {
   199                 // allow for Windows
   200                 return file.getCanonicalFile().getName().equals(n);
   201             } catch (IOException e) {
   202             }
   203         }
   204         return false;
   205     }
   207     private void ensureParentDirectoriesExist() throws IOException {
   208         if (!hasParents) {
   209             File parent = file.getParentFile();
   210             if (parent != null && !parent.exists()) {
   211                 if (!parent.mkdirs()) {
   212                     if (!parent.exists() || !parent.isDirectory()) {
   213                         throw new IOException("could not create parent directories");
   214                     }
   215                 }
   216             }
   217             hasParents = true;
   218         }
   219     }
   221     /**
   222      * Check if two file objects are equal.
   223      * Two RegularFileObjects are equal if the absolute paths of the underlying
   224      * files are equal.
   225      */
   226     @Override
   227     public boolean equals(Object other) {
   228         if (this == other)
   229             return true;
   231         if (!(other instanceof RegularFileObject))
   232             return false;
   234         RegularFileObject o = (RegularFileObject) other;
   235         return getAbsoluteFile().equals(o.getAbsoluteFile());
   236     }
   238     @Override
   239     public int hashCode() {
   240         return getAbsoluteFile().hashCode();
   241     }
   243     private File getAbsoluteFile() {
   244         File absFile = (absFileRef == null ? null : absFileRef.get());
   245         if (absFile == null) {
   246             absFile = file.getAbsoluteFile();
   247             absFileRef = new SoftReference<File>(absFile);
   248         }
   249         return absFile;
   250     }
   251 }

mercurial