### Eclipse Workspace Patch 1.0 #P org.eclipse.jdt.core Index: compiler/org/eclipse/jdt/internal/compiler/parser/JavadocParser.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/JavadocParser.java,v retrieving revision 1.77 diff -u -r1.77 JavadocParser.java --- compiler/org/eclipse/jdt/internal/compiler/parser/JavadocParser.java 24 Mar 2009 08:51:02 -0000 1.77 +++ compiler/org/eclipse/jdt/internal/compiler/parser/JavadocParser.java 16 Apr 2009 08:15:38 -0000 @@ -508,13 +508,13 @@ boolean valid = false; switch (firstChar) { case 'a': - if (length == TAG_AUTHOR_LENGTH && CharOperation.equals(TAG_AUTHOR, tagName, 0, length)) { + if (!this.inlineTagStarted && length == TAG_AUTHOR_LENGTH && CharOperation.equals(TAG_AUTHOR, tagName, 0, length)) { this.tagValue = TAG_AUTHOR_VALUE; this.tagWaitingForDescription = this.tagValue; } break; case 'c': - if (length == TAG_CATEGORY_LENGTH && CharOperation.equals(TAG_CATEGORY, tagName, 0, length)) { + if (!this.inlineTagStarted && length == TAG_CATEGORY_LENGTH && CharOperation.equals(TAG_CATEGORY, tagName, 0, length)) { this.tagValue = TAG_CATEGORY_VALUE; valid = parseIdentifierTag(false); // TODO (frederic) reconsider parameter value when @category will be significant in spec } else if (length == TAG_CODE_LENGTH && this.inlineTagStarted && CharOperation.equals(TAG_CODE, tagName, 0, length)) { @@ -523,7 +523,7 @@ } break; case 'd': - if (length == TAG_DEPRECATED_LENGTH && CharOperation.equals(TAG_DEPRECATED, tagName, 0, length)) { + if (!this.inlineTagStarted && length == TAG_DEPRECATED_LENGTH && CharOperation.equals(TAG_DEPRECATED, tagName, 0, length)) { this.deprecated = true; valid = true; this.tagValue = TAG_DEPRECATED_VALUE; @@ -536,7 +536,7 @@ } break; case 'e': - if (length == TAG_EXCEPTION_LENGTH && CharOperation.equals(TAG_EXCEPTION, tagName, 0, length)) { + if (!this.inlineTagStarted && length == TAG_EXCEPTION_LENGTH && CharOperation.equals(TAG_EXCEPTION, tagName, 0, length)) { this.tagValue = TAG_EXCEPTION_VALUE; valid = parseThrows(); } @@ -595,46 +595,39 @@ } break; case 'p': - if (length == TAG_PARAM_LENGTH && CharOperation.equals(TAG_PARAM, tagName, 0, length)) { + if (!this.inlineTagStarted && length == TAG_PARAM_LENGTH && CharOperation.equals(TAG_PARAM, tagName, 0, length)) { this.tagValue = TAG_PARAM_VALUE; valid = parseParam(); } break; case 'r': - if (length == TAG_RETURN_LENGTH && CharOperation.equals(TAG_RETURN, tagName, 0, length)) { + if (!this.inlineTagStarted && length == TAG_RETURN_LENGTH && CharOperation.equals(TAG_RETURN, tagName, 0, length)) { this.tagValue = TAG_RETURN_VALUE; valid = parseReturn(); } break; case 's': - if (length == TAG_SEE_LENGTH && CharOperation.equals(TAG_SEE, tagName, 0, length)) { - if (this.inlineTagStarted) { - // bug https://bugs.eclipse.org/bugs/show_bug.cgi?id=53290 - // Cannot have @see inside inline comment - valid = false; - if (this.reportProblems) { - this.sourceParser.problemReporter().javadocUnexpectedTag(this.tagSourceStart, this.tagSourceEnd); - } - } else { + if (!this.inlineTagStarted) { + if (length == TAG_SEE_LENGTH && CharOperation.equals(TAG_SEE, tagName, 0, length)) { this.tagValue = TAG_SEE_VALUE; valid = parseReference(); - } - } else if (length == TAG_SERIAL_LENGTH && CharOperation.equals(TAG_SERIAL, tagName, 0, length)) { - this.tagValue = TAG_SERIAL_VALUE; - this.tagWaitingForDescription = this.tagValue; - } else if (length == TAG_SERIAL_DATA_LENGTH && CharOperation.equals(TAG_SERIAL_DATA, tagName, 0, length)) { - this.tagValue = TAG_SERIAL_DATA_VALUE; - this.tagWaitingForDescription = this.tagValue; - } else if (length == TAG_SERIAL_FIELD_LENGTH && CharOperation.equals(TAG_SERIAL_FIELD, tagName, 0, length)) { - this.tagValue = TAG_SERIAL_FIELD_VALUE; - this.tagWaitingForDescription = this.tagValue; - } else if (length == TAG_SINCE_LENGTH && CharOperation.equals(TAG_SINCE, tagName, 0, length)) { - this.tagValue = TAG_SINCE_VALUE; - this.tagWaitingForDescription = this.tagValue; + } else if (length == TAG_SERIAL_LENGTH && CharOperation.equals(TAG_SERIAL, tagName, 0, length)) { + this.tagValue = TAG_SERIAL_VALUE; + this.tagWaitingForDescription = this.tagValue; + } else if (length == TAG_SERIAL_DATA_LENGTH && CharOperation.equals(TAG_SERIAL_DATA, tagName, 0, length)) { + this.tagValue = TAG_SERIAL_DATA_VALUE; + this.tagWaitingForDescription = this.tagValue; + } else if (length == TAG_SERIAL_FIELD_LENGTH && CharOperation.equals(TAG_SERIAL_FIELD, tagName, 0, length)) { + this.tagValue = TAG_SERIAL_FIELD_VALUE; + this.tagWaitingForDescription = this.tagValue; + } else if (length == TAG_SINCE_LENGTH && CharOperation.equals(TAG_SINCE, tagName, 0, length)) { + this.tagValue = TAG_SINCE_VALUE; + this.tagWaitingForDescription = this.tagValue; + } } break; case 't': - if (length == TAG_THROWS_LENGTH && CharOperation.equals(TAG_THROWS, tagName, 0, length)) { + if (!this.inlineTagStarted && length == TAG_THROWS_LENGTH && CharOperation.equals(TAG_THROWS, tagName, 0, length)) { this.tagValue = TAG_THROWS_VALUE; valid = parseThrows(); } @@ -664,7 +657,7 @@ if (this.reportProblems) this.sourceParser.problemReporter().javadocUnexpectedTag(this.tagSourceStart, this.tagSourceEnd); } } - } else if (length == TAG_VERSION_LENGTH && CharOperation.equals(TAG_VERSION, tagName, 0, length)) { + } else if (!this.inlineTagStarted && length == TAG_VERSION_LENGTH && CharOperation.equals(TAG_VERSION, tagName, 0, length)) { this.tagValue = TAG_VERSION_VALUE; this.tagWaitingForDescription = this.tagValue; } else { @@ -679,6 +672,10 @@ if (this.tagValue != TAG_OTHERS_VALUE && !this.inlineTagStarted) { this.lastBlockTagValue = this.tagValue; } + if (this.inlineTagStarted && this.reportProblems + && (this.tagValue >= JAVADOC_TAG_TYPE.length || JAVADOC_TAG_TYPE[this.tagValue] != TAG_TYPE_INLINE)) { + this.sourceParser.problemReporter().javadocUnexpectedTag(this.tagSourceStart, this.tagSourceEnd); + } return valid; } Index: compiler/org/eclipse/jdt/internal/compiler/parser/JavadocTagConstants.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/JavadocTagConstants.java,v retrieving revision 1.18 diff -u -r1.18 JavadocTagConstants.java --- compiler/org/eclipse/jdt/internal/compiler/parser/JavadocTagConstants.java 2 Sep 2008 08:09:13 -0000 1.18 +++ compiler/org/eclipse/jdt/internal/compiler/parser/JavadocTagConstants.java 16 Apr 2009 08:15:39 -0000 @@ -170,6 +170,33 @@ public final static int BLOCK_TAGS_LENGTH = BLOCK_TAGS.length; public final static int ALL_TAGS_LENGTH = BLOCK_TAGS_LENGTH+INLINE_TAGS_LENGTH; + public final static short TAG_TYPE_NONE = 0; + public final static short TAG_TYPE_INLINE = 1; + public final static short TAG_TYPE_BLOCK = 2; + + public static final short[] JAVADOC_TAG_TYPE = { + TAG_TYPE_NONE, // NO_TAG_VALUE = 0; + TAG_TYPE_BLOCK, // TAG_DEPRECATED_VALUE = 1; + TAG_TYPE_BLOCK, // TAG_PARAM_VALUE = 2; + TAG_TYPE_BLOCK, // TAG_RETURN_VALUE = 3; + TAG_TYPE_BLOCK, // TAG_THROWS_VALUE = 4; + TAG_TYPE_BLOCK, // TAG_EXCEPTION_VALUE = 5; + TAG_TYPE_BLOCK, // TAG_SEE_VALUE = 6; + TAG_TYPE_INLINE, // TAG_LINK_VALUE = 7; + TAG_TYPE_INLINE, // TAG_LINKPLAIN_VALUE = 8; + TAG_TYPE_INLINE, // TAG_INHERITDOC_VALUE = 9; + TAG_TYPE_INLINE, // TAG_VALUE_VALUE = 10; + TAG_TYPE_BLOCK, // TAG_CATEGORY_VALUE = 11; + TAG_TYPE_BLOCK, // TAG_AUTHOR_VALUE = 12; + TAG_TYPE_BLOCK, // TAG_SERIAL_VALUE = 13; + TAG_TYPE_BLOCK, // TAG_SERIAL_DATA_VALUE = 14; + TAG_TYPE_BLOCK, // TAG_SERIAL_FIELD_VALUE = 15; + TAG_TYPE_BLOCK, // TAG_SINCE_VALUE = 16; + TAG_TYPE_BLOCK, // TAG_VERSION_VALUE = 17; + TAG_TYPE_INLINE, // TAG_CODE_VALUE = 18; + TAG_TYPE_INLINE, // TAG_LITERAL_VALUE = 19; + TAG_TYPE_INLINE // TAG_DOC_ROOT_VALUE = 20; + }; /* * Tags usage */ #P org.eclipse.jdt.core.tests.compiler Index: src/org/eclipse/jdt/core/tests/compiler/regression/JavadocBugsTest.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/JavadocBugsTest.java,v retrieving revision 1.60 diff -u -r1.60 JavadocBugsTest.java --- src/org/eclipse/jdt/core/tests/compiler/regression/JavadocBugsTest.java 24 Mar 2009 08:51:00 -0000 1.60 +++ src/org/eclipse/jdt/core/tests/compiler/regression/JavadocBugsTest.java 16 Apr 2009 08:15:46 -0000 @@ -16,6 +16,7 @@ import org.eclipse.jdt.internal.compiler.classfmt.ClassFileConstants; import org.eclipse.jdt.internal.compiler.impl.CompilerOptions; +import org.eclipse.jdt.internal.compiler.parser.JavadocTagConstants; public class JavadocBugsTest extends JavadocTest { @@ -3318,23 +3319,33 @@ * @see 73995 */ public void testBug73995() { - runConformTest( + runNegativeTest( new String[] { "X.java", - "public class X {\n" + + "public class X extends Base {\n" + " /**\n" + " * @return {@link Object} \n" + " */\n" + " public int foo1() {return 0; }\n" + - " /** @return {@inheritedDoc} */\n" + + " /** @return {@inheritDoc} */\n" + " public int foo2() {return 0; }\n" + " /**\n" + " * @return\n" + " * {@unknown_tag}\n" + " */\n" + " public int foo3() {return 0; }\n" + - "}\n" - } + "}\n" + + "class Base {\n" + + "/** return \"The foo2 value\" */" + + "public int foo2(){return 0;}\n" + + "}" + }, + "----------\n" + + "1. ERROR in X.java (at line 10)\n" + + " * {@unknown_tag}\n" + + " ^^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" ); } @@ -8487,4 +8498,157 @@ JavacTestOptions.Excuse.EclipseWarningConfiguredAsError ); } +/** + * @bug 267833:[javadoc] Custom tags should not be allowed for inline tags + * @test Ensure that a warning is raised when customs tags are used as inline tags + * @see "https://bugs.eclipse.org/bugs/show_bug.cgi?id=267833" + */ +public void testBug267833() { + runNegativeTest( + new String[] { + "X.java", + "/**\n" + + "* Invalid custom tag {@custom \"Invalid\"} \n" + + "* @custom \"Valid\"\n" + + "*/\n" + + "public class X {\n" + + "}" + }, + "----------\n" + + "1. ERROR in X.java (at line 2)\n" + + " * Invalid custom tag {@custom \"Invalid\"} \n" + + " ^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + ); +} +/** + * Additional test for bug 267833 + * @test Ensure that the JavadocTagConstants.JAVADOC_TAG_TYPE array is up to date with the other arrays, such as + * JavadocTagConstants.TAG_NAMES, JavadocTagConstants.INLINE_TAGS and JavadocTagConstants.BLOCK_TAGS + */ +public void testBug267833_2() { + + assertEquals(JavadocTagConstants.TAG_NAMES.length,JavadocTagConstants.JAVADOC_TAG_TYPE.length); + + int tagsLength = JavadocTagConstants.TAG_NAMES.length; + nextTag:for (int index=0; index < tagsLength; index++) { + char[] tagName = JavadocTagConstants.TAG_NAMES[index]; + if (tagName.length > 0) { + for (int i=0; i < JavadocTagConstants.BLOCK_TAGS_LENGTH; i++) { + int length = JavadocTagConstants.BLOCK_TAGS[i].length; + for (int j=0; j < length; j++) { + if (tagName == JavadocTagConstants.BLOCK_TAGS[i][j]) { + assertEquals(JavadocTagConstants.JAVADOC_TAG_TYPE[index], JavadocTagConstants.TAG_TYPE_BLOCK); + continue nextTag; + } + } + } + for (int i=0; i < JavadocTagConstants.INLINE_TAGS_LENGTH; i++) { + int length = JavadocTagConstants.INLINE_TAGS[i].length; + for (int j=0; j < length; j++) { + if (tagName == JavadocTagConstants.INLINE_TAGS[i][j]) { + assertEquals(JavadocTagConstants.JAVADOC_TAG_TYPE[index], JavadocTagConstants.TAG_TYPE_INLINE); + continue nextTag; + } + } + } + } + assertEquals(JavadocTagConstants.JAVADOC_TAG_TYPE[index], JavadocTagConstants.TAG_TYPE_NONE); + } +} +/** + * Additional test for bug 267833 + * @test Ensure that a warning is raised when block tags are used as inline tags. + */ +public void testBug267833_3() { + runNegativeTest( + new String[] { + "X.java", + "public class X {\n" + + "/** \n" + + "* Description {@see value} , {@return value}, {@since value}, {@param i}, {@throws NullPointerException}\n" + + "* and more {@author jay}, {@category cat}, {@deprecated}, {@exception Exception}, {@version 1.1}\n" + + "* and more {@since 1.0}, {@serial 0L}, {@serialData data}, {@serialField field}" + + "* @param i\n" + + "* @return value\n" + + "* @throws NullPointerException \n" + + "*/\n" + + "public int foo(int i) {\n" + + " return 0;\n" + + "}\n" + + "}\n" }, + "----------\n" + + "1. ERROR in X.java (at line 3)\n" + + " * Description {@see value} , {@return value}, {@since value}, {@param i}, {@throws NullPointerException}\n" + + " ^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "2. ERROR in X.java (at line 3)\n" + + " * Description {@see value} , {@return value}, {@since value}, {@param i}, {@throws NullPointerException}\n" + + " ^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "3. ERROR in X.java (at line 3)\n" + + " * Description {@see value} , {@return value}, {@since value}, {@param i}, {@throws NullPointerException}\n" + + " ^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "4. ERROR in X.java (at line 3)\n" + + " * Description {@see value} , {@return value}, {@since value}, {@param i}, {@throws NullPointerException}\n" + + " ^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "5. ERROR in X.java (at line 3)\n" + + " * Description {@see value} , {@return value}, {@since value}, {@param i}, {@throws NullPointerException}\n" + + " ^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "6. ERROR in X.java (at line 4)\n" + + " * and more {@author jay}, {@category cat}, {@deprecated}, {@exception Exception}, {@version 1.1}\n" + + " ^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "7. ERROR in X.java (at line 4)\n" + + " * and more {@author jay}, {@category cat}, {@deprecated}, {@exception Exception}, {@version 1.1}\n" + + " ^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "8. ERROR in X.java (at line 4)\n" + + " * and more {@author jay}, {@category cat}, {@deprecated}, {@exception Exception}, {@version 1.1}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "9. ERROR in X.java (at line 4)\n" + + " * and more {@author jay}, {@category cat}, {@deprecated}, {@exception Exception}, {@version 1.1}\n" + + " ^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "10. ERROR in X.java (at line 4)\n" + + " * and more {@author jay}, {@category cat}, {@deprecated}, {@exception Exception}, {@version 1.1}\n" + + " ^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "11. ERROR in X.java (at line 5)\n" + + " * and more {@since 1.0}, {@serial 0L}, {@serialData data}, {@serialField field}* @param i\n" + + " ^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "12. ERROR in X.java (at line 5)\n" + + " * and more {@since 1.0}, {@serial 0L}, {@serialData data}, {@serialField field}* @param i\n" + + " ^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "13. ERROR in X.java (at line 5)\n" + + " * and more {@since 1.0}, {@serial 0L}, {@serialData data}, {@serialField field}* @param i\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "14. ERROR in X.java (at line 5)\n" + + " * and more {@since 1.0}, {@serial 0L}, {@serialData data}, {@serialField field}* @param i\n" + + " ^^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n"); +} + } \ No newline at end of file