From 9e0da7aa877afb5863b1b5c517d540e5b33a2d7c Mon Sep 17 00:00:00 2001 From: Roel Spilker Date: Mon, 10 Jan 2011 22:15:07 +0100 Subject: In javac7 the BaseFileObject and JavacFileManager have been moved from com/sun/tools/javac/util to com/sun/tools/javac/file --- .../lombok/javac/apt/EmptyLombokFileObject.java | 129 ++++++++++++++++++ .../javac/apt/InterceptingJavaFileManager.java | 150 ++------------------- .../javac/apt/InterceptingJavaFileObject.java | 55 ++++---- .../javac/apt/Javac6BaseFileObjectWrapper.java | 110 +++++++++++++++ .../javac/apt/Javac7BaseFileObjectWrapper.java | 111 +++++++++++++++ src/core/lombok/javac/apt/LombokFileObject.java | 31 +++++ src/core/lombok/javac/apt/LombokFileObjects.java | 95 +++++++++++++ 7 files changed, 515 insertions(+), 166 deletions(-) create mode 100644 src/core/lombok/javac/apt/EmptyLombokFileObject.java create mode 100644 src/core/lombok/javac/apt/Javac6BaseFileObjectWrapper.java create mode 100644 src/core/lombok/javac/apt/Javac7BaseFileObjectWrapper.java create mode 100644 src/core/lombok/javac/apt/LombokFileObject.java create mode 100644 src/core/lombok/javac/apt/LombokFileObjects.java (limited to 'src/core/lombok/javac') diff --git a/src/core/lombok/javac/apt/EmptyLombokFileObject.java b/src/core/lombok/javac/apt/EmptyLombokFileObject.java new file mode 100644 index 00000000..16fff9fc --- /dev/null +++ b/src/core/lombok/javac/apt/EmptyLombokFileObject.java @@ -0,0 +1,129 @@ +/* + * Copyright © 2010-2011 Reinier Zwitserloot, Roel Spilker and Robbert Jan Grootjans. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +package lombok.javac.apt; + +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.io.IOException; +import java.io.InputStream; +import java.io.OutputStream; +import java.io.OutputStreamWriter; +import java.io.Reader; +import java.io.StringReader; +import java.io.Writer; +import java.net.URI; +import java.nio.charset.Charset; +import java.nio.charset.CharsetDecoder; +import java.nio.charset.CodingErrorAction; + +import javax.lang.model.element.Modifier; +import javax.lang.model.element.NestingKind; + +// Can't use SimpleJavaFileObject so we copy/paste most of its content here, because javac doesn't follow the interface, +// and casts to its own BaseFileObject type. D'oh! +class EmptyLombokFileObject implements LombokFileObject { + private final String name; + private final Kind kind; + + public EmptyLombokFileObject(String name, Kind kind) { + this.name = name; + this.kind = kind; + } + + @Override public boolean isNameCompatible(String simpleName, Kind kind) { + String baseName = simpleName + kind.extension; + return kind.equals(getKind()) + && (baseName.equals(toUri().getPath()) + || toUri().getPath().endsWith("/" + baseName)); + } + + @Override public URI toUri() { + return URI.create(name); + } + + @Override public CharSequence getCharContent(boolean ignoreEncodingErrors) throws IOException { + return ""; + } + + @Override public InputStream openInputStream() throws IOException { + return new ByteArrayInputStream(new byte[0]); + } + + @Override public Reader openReader(boolean ignoreEncodingErrors) throws IOException { + return new StringReader(""); + } + + @Override public Writer openWriter() throws IOException { + return new OutputStreamWriter(openOutputStream()); + } + + @Override public OutputStream openOutputStream() throws IOException { + return new ByteArrayOutputStream(); + } + + @Override public long getLastModified() { + return 0L; + } + + @Override public boolean delete() { + return false; + } + + @Override public Kind getKind() { + return kind; + } + + @SuppressWarnings("all") + @Override public String getName() { + return toUri().getPath(); + } + + @Override public NestingKind getNestingKind() { + return null; + } + + @Override public Modifier getAccessLevel() { + return null; + } + + @Override public CharsetDecoder getDecoder(boolean ignoreEncodingErrors) { + CharsetDecoder decoder = Charset.forName("UTF-8").newDecoder(); + CodingErrorAction action = ignoreEncodingErrors ? CodingErrorAction.REPLACE : CodingErrorAction.REPORT; + return decoder.onMalformedInput(action).onUnmappableCharacter(action); + } + + @Override public boolean equals(Object obj) { + if (!(obj instanceof EmptyLombokFileObject)) { + return false; + } + if (obj == this) { + return true; + } + EmptyLombokFileObject other = (EmptyLombokFileObject) obj; + return name.equals(other.name) && kind.equals(other.kind); + } + + @Override public int hashCode() { + return name.hashCode() ^ kind.hashCode(); + } +} \ No newline at end of file diff --git a/src/core/lombok/javac/apt/InterceptingJavaFileManager.java b/src/core/lombok/javac/apt/InterceptingJavaFileManager.java index ef741c48..87aeb927 100644 --- a/src/core/lombok/javac/apt/InterceptingJavaFileManager.java +++ b/src/core/lombok/javac/apt/InterceptingJavaFileManager.java @@ -1,5 +1,5 @@ /* - * Copyright © 2010 Reinier Zwitserloot and Roel Spilker. + * Copyright © 2010-2011 Reinier Zwitserloot, Roel Spilker and Robbert Jan Grootjans. * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal @@ -21,168 +21,34 @@ */ package lombok.javac.apt; -import java.io.ByteArrayInputStream; -import java.io.ByteArrayOutputStream; import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; -import java.io.OutputStreamWriter; -import java.io.Reader; -import java.io.StringReader; -import java.io.Writer; -import java.net.URI; -import java.nio.charset.Charset; -import java.nio.charset.CharsetDecoder; -import java.nio.charset.CodingErrorAction; -import java.util.Iterator; -import java.util.Set; -import javax.lang.model.element.Modifier; -import javax.lang.model.element.NestingKind; import javax.tools.FileObject; +import javax.tools.ForwardingJavaFileManager; import javax.tools.JavaFileManager; import javax.tools.JavaFileObject; import javax.tools.JavaFileObject.Kind; -import com.sun.tools.javac.util.BaseFileObject; - import lombok.core.DiagnosticsReceiver; -final class InterceptingJavaFileManager implements JavaFileManager { - private final JavaFileManager delegate; +final class InterceptingJavaFileManager extends ForwardingJavaFileManager { + private final DiagnosticsReceiver diagnostics; InterceptingJavaFileManager(JavaFileManager original, DiagnosticsReceiver diagnostics) { - this.delegate = original; + super(original); this.diagnostics = diagnostics; } @Override public JavaFileObject getJavaFileForOutput(Location location, String className, final Kind kind, FileObject sibling) throws IOException { if (className.startsWith("lombok.dummy.ForceNewRound")) { final String name = className.replace(".", "/") + kind.extension; - // Can't use SimpleJavaFileObject so we copy/paste most of its content here, because javac doesn't follow the interface, - // and casts to its own BaseFileObject type. D'oh! - return new BaseFileObject() { - @Override public boolean isNameCompatible(String simpleName, Kind kind) { - String baseName = simpleName + kind.extension; - return kind.equals(getKind()) - && (baseName.equals(toUri().getPath()) - || toUri().getPath().endsWith("/" + baseName)); - } - - @Override public URI toUri() { - return URI.create(name); - } - - @Override public InputStream openInputStream() throws IOException { - return new ByteArrayInputStream(new byte[0]); - } - - @Override public OutputStream openOutputStream() throws IOException { - return new ByteArrayOutputStream(); - } - - @Override public CharSequence getCharContent(boolean ignoreEncodingErrors) throws IOException { - return ""; - } - - @Override public Writer openWriter() throws IOException { - return new OutputStreamWriter(openOutputStream()); - } - - @Override public long getLastModified() { - return 0L; - } - - @Override public boolean delete() { - return false; - } - - @Override public Kind getKind() { - return kind; - } - - @SuppressWarnings("all") - @Override public String getName() { - return toUri().getPath(); - } - - @Override public NestingKind getNestingKind() { - return null; - } - - @Override public Modifier getAccessLevel() { - return null; - } - - @Override public Reader openReader(boolean ignoreEncodingErrors) throws IOException { - return new StringReader(""); - } - - protected CharsetDecoder getDecoder(boolean ignoreEncodingErrors) { - CharsetDecoder decoder = Charset.forName("UTF-8").newDecoder(); - CodingErrorAction action = ignoreEncodingErrors ? CodingErrorAction.REPLACE : CodingErrorAction.REPORT; - return decoder.onMalformedInput(action).onUnmappableCharacter(action); - } - }; + return LombokFileObjects.createEmpty(fileManager, name, kind); } - JavaFileObject fileObject = delegate.getJavaFileForOutput(location, className, kind, sibling); + JavaFileObject fileObject = fileManager.getJavaFileForOutput(location, className, kind, sibling); if (kind != Kind.CLASS) { return fileObject; } - return new InterceptingJavaFileObject(fileObject, className, diagnostics); - } - - - - -/////////////////////// NOTHING CHANGED BELOW ////////////////////////////////////// - - @Override public void close() throws IOException { - delegate.close(); - } - - @Override public void flush() throws IOException { - delegate.flush(); - } - - @Override public ClassLoader getClassLoader(Location location) { - return delegate.getClassLoader(location); - } - - @Override public FileObject getFileForInput(Location location, String packageName, String relativeName) throws IOException { - return delegate.getFileForInput(location, packageName, relativeName); - } - - @Override public FileObject getFileForOutput(Location location, String packageName, String relativeName, FileObject sibling) throws IOException { - return delegate.getFileForOutput(location, packageName, relativeName, sibling); - } - - @Override public JavaFileObject getJavaFileForInput(Location location, String className, Kind kind) throws IOException { - return delegate.getJavaFileForInput(location, className, kind); - } - - @Override public boolean handleOption(String current, Iterator remaining) { - return delegate.handleOption(current, remaining); - } - - @Override public boolean hasLocation(Location location) { - return delegate.hasLocation(location); - } - - @Override public String inferBinaryName(Location location, JavaFileObject file) { - return delegate.inferBinaryName(location, file); - } - - @Override public boolean isSameFile(FileObject a, FileObject b) { - return delegate.isSameFile(a, b); - } - - @Override public Iterable list(Location location, String packageName, Set kinds, boolean recurse) throws IOException { - return delegate.list(location, packageName, kinds, recurse); - } - - @Override public int isSupportedOption(String option) { - return delegate.isSupportedOption(option); + return LombokFileObjects.createIntercepting(fileManager, fileObject, className, diagnostics); } } \ No newline at end of file diff --git a/src/core/lombok/javac/apt/InterceptingJavaFileObject.java b/src/core/lombok/javac/apt/InterceptingJavaFileObject.java index cd8b1f18..9b4b7496 100644 --- a/src/core/lombok/javac/apt/InterceptingJavaFileObject.java +++ b/src/core/lombok/javac/apt/InterceptingJavaFileObject.java @@ -1,5 +1,5 @@ /* - * Copyright © 2010 Reinier Zwitserloot and Roel Spilker. + * Copyright © 2010-2011 Reinier Zwitserloot, Roel Spilker and Robbert Jan Grootjans. * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal @@ -35,21 +35,21 @@ import javax.lang.model.element.Modifier; import javax.lang.model.element.NestingKind; import javax.tools.JavaFileObject; -import com.sun.tools.javac.util.BaseFileObject; - import lombok.Lombok; import lombok.core.DiagnosticsReceiver; import lombok.core.PostCompiler; -final class InterceptingJavaFileObject extends BaseFileObject { +final class InterceptingJavaFileObject implements LombokFileObject { private final JavaFileObject delegate; private final String fileName; private final DiagnosticsReceiver diagnostics; + private final Method decoderMethod; - public InterceptingJavaFileObject(JavaFileObject original, String fileName, DiagnosticsReceiver diagnostics) { + public InterceptingJavaFileObject(JavaFileObject original, String fileName, DiagnosticsReceiver diagnostics, Method decoderMethod) { this.delegate = original; this.fileName = fileName; this.diagnostics = diagnostics; + this.decoderMethod = decoderMethod; } @Override @@ -60,10 +60,35 @@ final class InterceptingJavaFileObject extends BaseFileObject { @Override public Writer openWriter() throws IOException { throw new UnsupportedOperationException("Can't use a write for class files"); -// return original.openWriter(); } + @Override public CharsetDecoder getDecoder(boolean ignoreEncodingErrors) { + if (decoderMethod == null) { + throw new UnsupportedOperationException(); + } + try { + return (CharsetDecoder) decoderMethod.invoke(delegate, ignoreEncodingErrors); + } catch (IllegalAccessException e) { + throw Lombok.sneakyThrow(e); + } catch (InvocationTargetException e) { + throw Lombok.sneakyThrow(e); + } + } + @Override public boolean equals(Object obj) { + if (!(obj instanceof InterceptingJavaFileObject)) { + return false; + } + if (obj == this) { + return true; + } + InterceptingJavaFileObject other = (InterceptingJavaFileObject) obj; + return fileName.equals(other.fileName) && delegate.equals(other.delegate); + } + + @Override public int hashCode() { + return fileName.hashCode() ^ delegate.hashCode(); + } /////////////////////// NOTHING CHANGED BELOW ////////////////////////////////////// @@ -123,22 +148,4 @@ final class InterceptingJavaFileObject extends BaseFileObject { public URI toUri() { return delegate.toUri(); } - - protected CharsetDecoder getDecoder(boolean ignoreEncodingErrors) { - if (delegate instanceof BaseFileObject) { - try { - Method m = BaseFileObject.class.getDeclaredMethod("getDecoder", boolean.class); - m.setAccessible(true); - return (CharsetDecoder) m.invoke(delegate, ignoreEncodingErrors); - } catch (NoSuchMethodException e) { - Lombok.sneakyThrow(e); - } catch (IllegalAccessException e) { - Lombok.sneakyThrow(e); - } catch (InvocationTargetException e) { - Lombok.sneakyThrow(e); - } - } - - throw new UnsupportedOperationException(); - } } diff --git a/src/core/lombok/javac/apt/Javac6BaseFileObjectWrapper.java b/src/core/lombok/javac/apt/Javac6BaseFileObjectWrapper.java new file mode 100644 index 00000000..f1f33426 --- /dev/null +++ b/src/core/lombok/javac/apt/Javac6BaseFileObjectWrapper.java @@ -0,0 +1,110 @@ +/* + * Copyright © 2010-2011 Reinier Zwitserloot, Roel Spilker and Robbert Jan Grootjans. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +package lombok.javac.apt; + +import java.io.IOException; +import java.io.InputStream; +import java.io.OutputStream; +import java.io.Reader; +import java.io.Writer; +import java.net.URI; +import java.nio.charset.CharsetDecoder; + +import javax.lang.model.element.Modifier; +import javax.lang.model.element.NestingKind; + +class Javac6BaseFileObjectWrapper extends com.sun.tools.javac.util.BaseFileObject { + private final LombokFileObject delegate; + + public Javac6BaseFileObjectWrapper(LombokFileObject delegate) { + this.delegate = delegate; + } + + @Override public boolean isNameCompatible(String simpleName, Kind kind) { + return delegate.isNameCompatible(simpleName, kind); + } + + @Override public URI toUri() { + return delegate.toUri(); + } + + @SuppressWarnings("all") + @Override public String getName() { + return delegate.getName(); + } + + @Override public CharSequence getCharContent(boolean ignoreEncodingErrors) throws IOException { + return delegate.getCharContent(ignoreEncodingErrors); + } + + @Override public InputStream openInputStream() throws IOException { + return delegate.openInputStream(); + } + + @Override public Reader openReader(boolean ignoreEncodingErrors) throws IOException { + return delegate.openReader(ignoreEncodingErrors); + } + + @Override public Writer openWriter() throws IOException { + return delegate.openWriter(); + } + + @Override public OutputStream openOutputStream() throws IOException { + return delegate.openOutputStream(); + } + + @Override public long getLastModified() { + return delegate.getLastModified(); + } + + @Override public boolean delete() { + return delegate.delete(); + } + + @Override public Kind getKind() { + return delegate.getKind(); + } + + @Override public NestingKind getNestingKind() { + return delegate.getNestingKind(); + } + + @Override public Modifier getAccessLevel() { + return delegate.getAccessLevel(); + } + + protected CharsetDecoder getDecoder(boolean ignoreEncodingErrors) { + return delegate.getDecoder(ignoreEncodingErrors); + } + + @Override public boolean equals(Object obj) { + if (!(obj instanceof Javac6BaseFileObjectWrapper)) { + return false; + } + return delegate.equals(((Javac6BaseFileObjectWrapper)obj).delegate); + } + + @Override public int hashCode() { + return delegate.hashCode(); + } +} \ No newline at end of file diff --git a/src/core/lombok/javac/apt/Javac7BaseFileObjectWrapper.java b/src/core/lombok/javac/apt/Javac7BaseFileObjectWrapper.java new file mode 100644 index 00000000..81cf834a --- /dev/null +++ b/src/core/lombok/javac/apt/Javac7BaseFileObjectWrapper.java @@ -0,0 +1,111 @@ +/* + * Copyright © 2010-2011 Reinier Zwitserloot, Roel Spilker and Robbert Jan Grootjans. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +package lombok.javac.apt; + +import java.io.IOException; +import java.io.InputStream; +import java.io.OutputStream; +import java.io.Reader; +import java.io.Writer; +import java.net.URI; +import java.nio.charset.CharsetDecoder; + +import javax.lang.model.element.Modifier; +import javax.lang.model.element.NestingKind; + +class Javac7BaseFileObjectWrapper extends com.sun.tools.javac.file.BaseFileObject { + private final LombokFileObject delegate; + + public Javac7BaseFileObjectWrapper(com.sun.tools.javac.file.JavacFileManager jfm, LombokFileObject delegate) { + super(jfm); + this.delegate = delegate; + } + + @Override public boolean isNameCompatible(String simpleName, Kind kind) { + return delegate.isNameCompatible(simpleName, kind); + } + + @Override public URI toUri() { + return delegate.toUri(); + } + + @SuppressWarnings("all") + @Override public String getName() { + return delegate.getName(); + } + + @Override public CharSequence getCharContent(boolean ignoreEncodingErrors) throws IOException { + return delegate.getCharContent(ignoreEncodingErrors); + } + + @Override public InputStream openInputStream() throws IOException { + return delegate.openInputStream(); + } + + @Override public Reader openReader(boolean ignoreEncodingErrors) throws IOException { + return delegate.openReader(ignoreEncodingErrors); + } + + @Override public Writer openWriter() throws IOException { + return delegate.openWriter(); + } + + @Override public OutputStream openOutputStream() throws IOException { + return delegate.openOutputStream(); + } + + @Override public long getLastModified() { + return delegate.getLastModified(); + } + + @Override public boolean delete() { + return delegate.delete(); + } + + @Override public Kind getKind() { + return delegate.getKind(); + } + + @Override public NestingKind getNestingKind() { + return delegate.getNestingKind(); + } + + @Override public Modifier getAccessLevel() { + return delegate.getAccessLevel(); + } + + protected CharsetDecoder getDecoder(boolean ignoreEncodingErrors) { + return delegate.getDecoder(ignoreEncodingErrors); + } + + @Override public boolean equals(Object obj) { + if (!(obj instanceof Javac7BaseFileObjectWrapper)) { + return false; + } + return delegate.equals(((Javac7BaseFileObjectWrapper)obj).delegate); + } + + @Override public int hashCode() { + return delegate.hashCode(); + } +} \ No newline at end of file diff --git a/src/core/lombok/javac/apt/LombokFileObject.java b/src/core/lombok/javac/apt/LombokFileObject.java new file mode 100644 index 00000000..24191e21 --- /dev/null +++ b/src/core/lombok/javac/apt/LombokFileObject.java @@ -0,0 +1,31 @@ +/* + * Copyright © 2010-2011 Reinier Zwitserloot, Roel Spilker and Robbert Jan Grootjans. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +package lombok.javac.apt; + +import java.nio.charset.CharsetDecoder; + +import javax.tools.JavaFileObject; + +interface LombokFileObject extends JavaFileObject { + CharsetDecoder getDecoder(boolean ignoreEncodingErrors); +} diff --git a/src/core/lombok/javac/apt/LombokFileObjects.java b/src/core/lombok/javac/apt/LombokFileObjects.java new file mode 100644 index 00000000..b868c847 --- /dev/null +++ b/src/core/lombok/javac/apt/LombokFileObjects.java @@ -0,0 +1,95 @@ +/* + * Copyright © 2010-2011 Reinier Zwitserloot, Roel Spilker and Robbert Jan Grootjans. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +package lombok.javac.apt; + +import java.lang.reflect.Method; + +import javax.tools.JavaFileManager; +import javax.tools.JavaFileObject; +import javax.tools.JavaFileObject.Kind; + +import lombok.core.DiagnosticsReceiver; + +//Can't use SimpleJavaFileObject so we copy/paste most of its content here, because javac doesn't follow the interface, +//and casts to its own BaseFileObject type. D'oh! +final class LombokFileObjects { + + private enum Compiler { + JAVAC6 { + @Override public JavaFileObject wrap(JavaFileManager fileManager, LombokFileObject fileObject) { + return new Javac6BaseFileObjectWrapper(fileObject); + } + }, + JAVAC7 { + @Override public JavaFileObject wrap(JavaFileManager fileManager, LombokFileObject fileObject) { + return new Javac7BaseFileObjectWrapper((com.sun.tools.javac.file.JavacFileManager)fileManager, fileObject); + } + }; + + abstract JavaFileObject wrap(JavaFileManager fileManager, LombokFileObject fileObject); + } + + private static final Compiler compiler; + private static final Method decoderMethod; + + static { + Compiler c = null; + Method m = null; + try { + // In javac6, the BaseFileObject is located in + // com.sun.tools.javac.util + Class clazz = Class.forName("com.sun.tools.javac.util.BaseFileObject"); + c = Compiler.JAVAC6; + try { + // The getDecoder method is not always present in javac6 + m = clazz.getDeclaredMethod("getDecoder", boolean.class); + } catch (NoSuchMethodException e) {} + } catch (ClassNotFoundException cnfe) { + // In javac7, the BaseFileObject has been moved to the package + // com.sun.tools.javac.file + try { + Class clazz = Class.forName("com.sun.tools.javac.file.BaseFileObject"); + c = Compiler.JAVAC7; + try { + m = clazz.getDeclaredMethod("getDecoder", boolean.class); + } catch (NoSuchMethodException e) {} + } catch (ClassNotFoundException cnfe2) { + } + } + compiler = c; + if (m != null) { + m.setAccessible(true); + } + decoderMethod = m; + } + + private LombokFileObjects() {} + + static JavaFileObject createEmpty(JavaFileManager fileManager, String name, Kind kind) { + return compiler.wrap(fileManager, new EmptyLombokFileObject(name, kind)); + } + + static JavaFileObject createIntercepting(JavaFileManager fileManager, JavaFileObject delegate, String fileName, DiagnosticsReceiver diagnostics) { + return compiler.wrap(fileManager, new InterceptingJavaFileObject(delegate, fileName, diagnostics, decoderMethod)); + } +} -- cgit