-
Bug
-
Resolution: Fixed
-
P3
-
6u1, 7
-
b114
-
generic
-
generic
-
Verified
Issue | Fix Version | Assignee | Priority | Status | Resolution | Resolved In Build |
---|---|---|---|---|---|---|
JDK-2185328 | 6-pool | Joe Darcy | P3 | Closed | Not an Issue | |
JDK-2208055 | OpenJDK6 | James Holmlund | P3 | Resolved | Fixed | b23 |
javax.annotation.processing.Filer has two methods: createResource() and
getResource().
The spec for getResource() and createResource() states that
IllegalArgumentException is thrown if relativeName is not relative,
IOException is thrown if the file cannot be created/opened.
On the top of Filer interface description there is a spec excerpt:
====
A relative name is a non-null, non-empty sequence of path segments
separated by '/'; '.' and '..' are invalid path segments. A valid
relative name must match the "path-rootless" rule of RFC 3986, section 3.3.
====
So the following relative names are invalid: "/boo", "goo/../hoo",
"./ioo", "".
And the filer should throw IllegalArgumentException if it uses the
relative names above when
creating or getting resources. As a variant the filer may throw
IOException when getResource is trying to open nonexistent file.
However, getting or creating resource with invalid relative names causes
to throwing neither
IllegalArgumentException nor IOException.
# javac -cp . -processor tmp.InvalidRelativeNameProcessor java.lang.Object
You may reproduce the behavior using following processor class (you need
to uncomment either writer,
or reader, or output stream, or inputstream block of code marked as 1,
2, 3, and 4). Also you may substitute StandardLocation.SOURCE_OUTPUT to
StandardLocation.CLASS_OUTPUT and run it once more.
package tmp;
import java.io.InputStream;
import java.io.Reader;
import java.io.Writer;
import javax.annotation.processing.AbstractProcessor;
import javax.annotation.processing.RoundEnvironment;
import javax.annotation.processing.Filer;
import javax.lang.model.element.TypeElement;
import javax.lang.model.element.Element;
import javax.lang.model.SourceVersion;
import java.util.Set;
import java.util.HashSet;
import java.io.IOException;
import java.io.OutputStream;
import javax.tools.JavaFileManager;
import javax.tools.StandardLocation;
public class InvalidRelativeNameProcessor extends AbstractProcessor {
String[] invalidRelativeNames = {
"/boo", "goo/../hoo", "./ioo", ""
};
public Set<String> getSupportedAnnotationTypes() {
return new HashSet<String>() {{add("*");}};
}
public SourceVersion getSupportedSourceVersion() {
return SourceVersion.RELEASE_6;
}
public boolean process(Set<? extends TypeElement> annotations, RoundEnvironment roundEnv) {
boolean passed = true;
if(roundEnv.processingOver()) {
Filer filer = processingEnv.getFiler();
for (String relative: invalidRelativeNames) {
try {
// Writer writer = filer.createResource( // 1
// StandardLocation.SOURCE_OUTPUT, "", relative).openWriter(); // 1
// writer.close(); // 1
// Reader reader = filer.createResource( // 2
// StandardLocation.SOURCE_OUTPUT, "", relative).openReader(true); // 2
// reader.close(); // 2
// OutputStream out = filer.createResource( // 3
// StandardLocation.SOURCE_OUTPUT, "", relative).openOutputStream(); // 3
// out.close(); // 3
// InputStream in = filer.createResource( // 4
// StandardLocation.SOURCE_OUTPUT, "", relative).openInputStream(); // 4
// in.close(); // 4
System.out.println("relative path: " + relative);
} catch (IllegalArgumentException expected) {
} catch (IOException expected) {
} catch (Exception e) {
passed = false;
System.out.println("relative path: " + relative + ", thrown: " + e);
}
}
}
return true;
}
}
As a result of running these tests relative names "goo/../hoo" and
"./ioo" doesn't cause to throwing either IllegalArgumentException, or
IOException. When we are trying to write a resource there are no
exception thrown at all. When we are trying to get resource then
unexpected java.lang.IllegalStateException is thrown.
I suppose it is unexpected behavior.
getResource().
The spec for getResource() and createResource() states that
IllegalArgumentException is thrown if relativeName is not relative,
IOException is thrown if the file cannot be created/opened.
On the top of Filer interface description there is a spec excerpt:
====
A relative name is a non-null, non-empty sequence of path segments
separated by '/'; '.' and '..' are invalid path segments. A valid
relative name must match the "path-rootless" rule of RFC 3986, section 3.3.
====
So the following relative names are invalid: "/boo", "goo/../hoo",
"./ioo", "".
And the filer should throw IllegalArgumentException if it uses the
relative names above when
creating or getting resources. As a variant the filer may throw
IOException when getResource is trying to open nonexistent file.
However, getting or creating resource with invalid relative names causes
to throwing neither
IllegalArgumentException nor IOException.
# javac -cp . -processor tmp.InvalidRelativeNameProcessor java.lang.Object
You may reproduce the behavior using following processor class (you need
to uncomment either writer,
or reader, or output stream, or inputstream block of code marked as 1,
2, 3, and 4). Also you may substitute StandardLocation.SOURCE_OUTPUT to
StandardLocation.CLASS_OUTPUT and run it once more.
package tmp;
import java.io.InputStream;
import java.io.Reader;
import java.io.Writer;
import javax.annotation.processing.AbstractProcessor;
import javax.annotation.processing.RoundEnvironment;
import javax.annotation.processing.Filer;
import javax.lang.model.element.TypeElement;
import javax.lang.model.element.Element;
import javax.lang.model.SourceVersion;
import java.util.Set;
import java.util.HashSet;
import java.io.IOException;
import java.io.OutputStream;
import javax.tools.JavaFileManager;
import javax.tools.StandardLocation;
public class InvalidRelativeNameProcessor extends AbstractProcessor {
String[] invalidRelativeNames = {
"/boo", "goo/../hoo", "./ioo", ""
};
public Set<String> getSupportedAnnotationTypes() {
return new HashSet<String>() {{add("*");}};
}
public SourceVersion getSupportedSourceVersion() {
return SourceVersion.RELEASE_6;
}
public boolean process(Set<? extends TypeElement> annotations, RoundEnvironment roundEnv) {
boolean passed = true;
if(roundEnv.processingOver()) {
Filer filer = processingEnv.getFiler();
for (String relative: invalidRelativeNames) {
try {
// Writer writer = filer.createResource( // 1
// StandardLocation.SOURCE_OUTPUT, "", relative).openWriter(); // 1
// writer.close(); // 1
// Reader reader = filer.createResource( // 2
// StandardLocation.SOURCE_OUTPUT, "", relative).openReader(true); // 2
// reader.close(); // 2
// OutputStream out = filer.createResource( // 3
// StandardLocation.SOURCE_OUTPUT, "", relative).openOutputStream(); // 3
// out.close(); // 3
// InputStream in = filer.createResource( // 4
// StandardLocation.SOURCE_OUTPUT, "", relative).openInputStream(); // 4
// in.close(); // 4
System.out.println("relative path: " + relative);
} catch (IllegalArgumentException expected) {
} catch (IOException expected) {
} catch (Exception e) {
passed = false;
System.out.println("relative path: " + relative + ", thrown: " + e);
}
}
}
return true;
}
}
As a result of running these tests relative names "goo/../hoo" and
"./ioo" doesn't cause to throwing either IllegalArgumentException, or
IOException. When we are trying to write a resource there are no
exception thrown at all. When we are trying to get resource then
unexpected java.lang.IllegalStateException is thrown.
I suppose it is unexpected behavior.
- backported by
-
JDK-2208055 Invalid relative names for Filer.createResource and Filer.getResource
- Resolved
-
JDK-2185328 Invalid relative names for Filer.createResource and Filer.getResource
- Closed
- relates to
-
JDK-6791060 java.net.URI should be updated for RFC 3986
- Closed
-
JDK-6791041 Filer.createResource throws IAE "relativeName is invalid" for legitimate path ".something"
- Closed
-
JDK-6999891 DefaultFileManager incorrect
- Closed