### Eclipse Workspace Patch 1.0 #P org.eclipse.jdt.core Index: compiler/org/eclipse/jdt/internal/compiler/ast/Javadoc.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/ast/Javadoc.java,v retrieving revision 1.64 diff -u -r1.64 Javadoc.java --- compiler/org/eclipse/jdt/internal/compiler/ast/Javadoc.java 8 Jan 2009 20:51:05 -0000 1.64 +++ compiler/org/eclipse/jdt/internal/compiler/ast/Javadoc.java 24 Mar 2009 05:13:08 -0000 @@ -27,7 +27,7 @@ public TypeReference[] exceptionReferences; // @throws, @exception public JavadocReturnStatement returnStatement; // @return public Expression[] seeReferences; // @see - public long inheritedPositions = -1; + public long[] inheritedPositions = null; // bug https://bugs.eclipse.org/bugs/show_bug.cgi?id=51600 // Store param references for tag with invalid syntax public JavadocSingleNameReference[] invalidParameters; // @param @@ -184,7 +184,16 @@ * Resolve type javadoc */ public void resolve(ClassScope scope) { - + // https://bugs.eclipse.org/bugs/show_bug.cgi?id=247037, @inheritDoc tag cannot + // be used in the documentation comment for a class or interface. + if (this.inheritedPositions != null) { + int length = this.inheritedPositions.length; + for (int i = 0; i < length; ++i) { + int start = (int) (this.inheritedPositions[i] >>> 32); + int end = (int) this.inheritedPositions[i]; + scope.problemReporter().javadocUnexpectedTag(start, end); + } + } // @param tags int paramTagsSize = this.paramReferences == null ? 0 : this.paramReferences.length; for (int i = 0; i < paramTagsSize; i++) { @@ -303,11 +312,14 @@ } // Store if a reference exists to an overriden method/constructor or the method is in a local type, - boolean reportMissing = methDecl == null || !((overriding && this.inheritedPositions != -1) || superRef || (methDecl.binding.declaringClass != null && methDecl.binding.declaringClass.isLocalType())); - if (!overriding && this.inheritedPositions != -1) { - int start = (int) (this.inheritedPositions >>> 32); - int end = (int) this.inheritedPositions; - methScope.problemReporter().javadocUnexpectedTag(start, end); + boolean reportMissing = methDecl == null || !((overriding && this.inheritedPositions != null) || superRef || (methDecl.binding.declaringClass != null && methDecl.binding.declaringClass.isLocalType())); + if (!overriding && this.inheritedPositions != null) { + int length = this.inheritedPositions.length; + for (int i = 0; i < length; ++i) { + int start = (int) (this.inheritedPositions[i] >>> 32); + int end = (int) this.inheritedPositions[i]; + methScope.problemReporter().javadocUnexpectedTag(start, end); + } } // @param tags Index: formatter/org/eclipse/jdt/internal/formatter/FormatterCommentParser.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/formatter/org/eclipse/jdt/internal/formatter/FormatterCommentParser.java,v retrieving revision 1.24 diff -u -r1.24 FormatterCommentParser.java --- formatter/org/eclipse/jdt/internal/formatter/FormatterCommentParser.java 7 Mar 2009 00:59:01 -0000 1.24 +++ formatter/org/eclipse/jdt/internal/formatter/FormatterCommentParser.java 24 Mar 2009 05:13:10 -0000 @@ -493,13 +493,8 @@ break; case 'i': if (length == TAG_INHERITDOC_LENGTH && CharOperation.equals(TAG_INHERITDOC, tagName)) { - // inhibits inherited flag when tags have been already stored - // see bug https://bugs.eclipse.org/bugs/show_bug.cgi?id=51606 - // Note that for DOM_PARSER, nodes stack may be not empty even no '@' tag - // was encountered in comment. But it cannot be the case for COMPILER_PARSER - // and so is enough as it is only this parser which signals the missing tag warnings... - if (this.astPtr==-1) { - this.inheritedPositions = (((long) this.tagSourceStart) << 32) + this.tagSourceEnd; + if (this.reportProblems) { + recordInheritedPosition((((long) this.tagSourceStart) << 32) + this.tagSourceEnd); } valid = true; this.tagValue = TAG_INHERITDOC_VALUE; Index: dom/org/eclipse/jdt/core/dom/DocCommentParser.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/dom/org/eclipse/jdt/core/dom/DocCommentParser.java,v retrieving revision 1.38 diff -u -r1.38 DocCommentParser.java --- dom/org/eclipse/jdt/core/dom/DocCommentParser.java 27 Jun 2008 16:03:46 -0000 1.38 +++ dom/org/eclipse/jdt/core/dom/DocCommentParser.java 24 Mar 2009 05:13:10 -0000 @@ -420,13 +420,8 @@ break; case 'i': if (length == TAG_INHERITDOC_LENGTH && CharOperation.equals(TAG_INHERITDOC, tagName)) { - // inhibits inherited flag when tags have been already stored - // see bug https://bugs.eclipse.org/bugs/show_bug.cgi?id=51606 - // Note that for DOM_PARSER, nodes stack may be not empty even no '@' tag - // was encountered in comment. But it cannot be the case for COMPILER_PARSER - // and so is enough as it is only this parser which signals the missing tag warnings... - if (this.astPtr==-1) { - this.inheritedPositions = (((long) this.tagSourceStart) << 32) + this.tagSourceEnd; + if (this.reportProblems) { + recordInheritedPosition((((long) this.tagSourceStart) << 32) + this.tagSourceEnd); } this.tagValue = TAG_INHERITDOC_VALUE; } else { 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.76 diff -u -r1.76 JavadocParser.java --- compiler/org/eclipse/jdt/internal/compiler/parser/JavadocParser.java 16 Feb 2009 17:53:44 -0000 1.76 +++ compiler/org/eclipse/jdt/internal/compiler/parser/JavadocParser.java 24 Mar 2009 05:13:10 -0000 @@ -543,15 +543,26 @@ break; case 'i': if (length == TAG_INHERITDOC_LENGTH && CharOperation.equals(TAG_INHERITDOC, tagName, 0, length)) { - // inhibits inherited flag when tags have been already stored - // see bug https://bugs.eclipse.org/bugs/show_bug.cgi?id=51606 - // Note that for DOM_PARSER, nodes stack may be not empty even no '@' tag - // was encountered in comment. But it cannot be the case for COMPILER_PARSER - // and so is enough as it is only this parser which signals the missing tag warnings... - if (this.astPtr==-1) { - this.inheritedPositions = (((long) this.tagSourceStart) << 32) + this.tagSourceEnd; + // https://bugs.eclipse.org/bugs/show_bug.cgi?id=247037, @inheritDoc usage is illegal + // outside of few block tags and the main description. + switch (this.lastBlockTagValue) { + case TAG_RETURN_VALUE: + case TAG_THROWS_VALUE: + case TAG_EXCEPTION_VALUE: + case TAG_PARAM_VALUE: + case NO_TAG_VALUE: // Still in main description + valid = true; + if (this.reportProblems) { + recordInheritedPosition((((long) this.tagSourceStart) << 32) + this.tagSourceEnd); + } + break; + default: + valid = false; + if (this.reportProblems) { + this.sourceParser.problemReporter().javadocUnexpectedTag(this.tagSourceStart, + this.tagSourceEnd); + } } - valid = true; this.tagValue = TAG_INHERITDOC_VALUE; } break; @@ -665,6 +676,9 @@ break; } this.textStart = this.index; + if (this.tagValue != TAG_OTHERS_VALUE && !this.inlineTagStarted) { + this.lastBlockTagValue = this.tagValue; + } return valid; } @@ -860,6 +874,11 @@ this.tagWaitingForDescription = NO_TAG_VALUE; // Set positions + if (this.inheritedPositions != null && this.inheritedPositionsPtr != this.inheritedPositions.length) { + // Compact array by shrinking. + System.arraycopy(this.inheritedPositions, 0, + this.inheritedPositions = new long[this.inheritedPositionsPtr], 0, this.inheritedPositionsPtr); + } this.docComment.inheritedPositions = this.inheritedPositions; this.docComment.valuePositions = this.validValuePositions != -1 ? this.validValuePositions : this.invalidValuePositions; Index: compiler/org/eclipse/jdt/internal/compiler/parser/AbstractCommentParser.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core/compiler/org/eclipse/jdt/internal/compiler/parser/AbstractCommentParser.java,v retrieving revision 1.87 diff -u -r1.87 AbstractCommentParser.java --- compiler/org/eclipse/jdt/internal/compiler/parser/AbstractCommentParser.java 9 Jan 2009 15:10:20 -0000 1.87 +++ compiler/org/eclipse/jdt/internal/compiler/parser/AbstractCommentParser.java 24 Mar 2009 05:13:09 -0000 @@ -51,9 +51,13 @@ public boolean reportProblems; protected long complianceLevel; protected long sourceLevel; + + // Support for {@inheritDoc} + protected long [] inheritedPositions; + protected int inheritedPositionsPtr; + private final static int INHERITED_POSITIONS_ARRAY_INCREMENT = 4; // Results - protected long inheritedPositions; protected boolean deprecated; protected Object returnStatement; @@ -74,6 +78,7 @@ protected boolean abort = false; protected int kind; protected int tagValue = NO_TAG_VALUE; + protected int lastBlockTagValue = NO_TAG_VALUE; // Line pointers private int linePtr, lastLinePtr; @@ -129,7 +134,8 @@ this.inlineTagStart = -1; this.lineStarted = false; this.returnStatement = null; - this.inheritedPositions = -1; + this.inheritedPositions = null; + this.lastBlockTagValue = NO_TAG_VALUE; this.deprecated = false; this.lastLinePtr = getLineNumber(this.javadocEnd); this.textStart = -1; @@ -1467,6 +1473,21 @@ return token; } + protected void recordInheritedPosition(long position) { + if (this.inheritedPositions == null) { + this.inheritedPositions = new long[INHERITED_POSITIONS_ARRAY_INCREMENT]; + this.inheritedPositionsPtr = 0; + } else { + if (this.inheritedPositionsPtr == this.inheritedPositions.length) { + System.arraycopy( + this.inheritedPositions, 0, + this.inheritedPositions = new long[this.inheritedPositionsPtr + INHERITED_POSITIONS_ARRAY_INCREMENT], 0, + this.inheritedPositionsPtr); + } + } + this.inheritedPositions[this.inheritedPositionsPtr++] = position; + } + /* * Refresh start position and length of an inline tag. */ #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.59 diff -u -r1.59 JavadocBugsTest.java --- src/org/eclipse/jdt/core/tests/compiler/regression/JavadocBugsTest.java 16 Feb 2009 17:53:47 -0000 1.59 +++ src/org/eclipse/jdt/core/tests/compiler/regression/JavadocBugsTest.java 24 Mar 2009 05:13:16 -0000 @@ -1729,9 +1729,12 @@ * Bug 51606: [Javadoc] Compiler should complain when tag name is not correct * @see 51606 */ +// Cleaned up this test as part of fix for https://bugs.eclipse.org/bugs/show_bug.cgi?id=247037 +// We should not complain about the missing @param tag for Y.foo at all, since the comments are +// automatically inherited. public void testBug51606() { this.reportMissingJavadocTags = CompilerOptions.ERROR; - runNegativeTest( + runConformTest( new String[] { "X.java", "public class X {\n" + @@ -1751,13 +1754,7 @@ " }\n" + "}\n" }, - "----------\n" + - "1. ERROR in Y.java (at line 5)\n" + - " public void foo(int a, int b) {\n" + - " ^\n" + - "Javadoc: Missing tag for parameter b\n" + - "----------\n", - JavacTestOptions.Excuse.EclipseWarningConfiguredAsError + "" ); } public void testBug51606a() { @@ -8321,4 +8318,173 @@ } } +// https://bugs.eclipse.org/bugs/show_bug.cgi?id=247037, make sure that we complain when @inheritdoc +// is used where it is outlawed by the specs. This test verifies that we complain when @inheritDoc +// is used with classes and interfaces. +public void testBug247037() { + this.reportMissingJavadocTags = CompilerOptions.ERROR; + runNegativeTest( + new String[] { + "X.java", + "/**\n" + + " * {@inheritDoc}\n" + // error, cannot be applied to a class + " */\n" + + "public class X {\n" + + "}\n" + + "/**\n" + + " * {@inheritDoc}\n" + // error, cannot be applied to interfaces. + " */" + + "interface Blah {\n" + + " void BlahBlah();\n" + + "}\n" + }, + "----------\n" + + "1. ERROR in X.java (at line 2)\n" + + " * {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "2. ERROR in X.java (at line 7)\n" + + " * {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n", + JavacTestOptions.Excuse.EclipseWarningConfiguredAsError + ); +} + +//https://bugs.eclipse.org/bugs/show_bug.cgi?id=247037, make sure that we complain when @inheritdoc +//is used where it is outlawed by the specs. Here we test that when @inheritDoc is applied to a +// field or constructor, we complain. +public void testBug247037b() { + this.reportMissingJavadocTags = CompilerOptions.ERROR; + runNegativeTest( + new String[] { + "X.java", + "public class X {\n" + + "}\n" + + "class Y extends X {\n" + + " /**\n" + + " * {@inheritDoc}\n" + // error, cannot be applied to a field + " */\n" + + " public int field = 10;\n" + + " /**\n" + + " * @param x {@inheritDoc}\n" + // error, cannot be applied to a constructor + " */\n" + + " Y(int x) {}\n" + + "}\n" + }, + "----------\n" + + "1. ERROR in X.java (at line 5)\n" + + " * {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "2. ERROR in X.java (at line 9)\n" + + " * @param x {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n", + JavacTestOptions.Excuse.EclipseWarningConfiguredAsError + ); +} +//https://bugs.eclipse.org/bugs/show_bug.cgi?id=247037, make sure that we complain when @inheritdoc +//is used where it is outlawed by the specs. In this test we test the use of @inheritedDoc in some +// block tags. +public void testBug247037c() { + this.reportMissingJavadocTags = CompilerOptions.ERROR; + runNegativeTest( + new String[] { + "X.java", + "public class X {\n" + + " /**\n" + + " * @since 1.0\n" + + " * @return Blah\n" + + " * @param blah Blah Blah\n" + + " * @throws Exception When something is wrong\n" + + " */\n" + + " public int m(int blah) throws Exception {\n" + + " return 0;\n" + + " }\n" + + "}\n" + + "class Y extends X {\n" + + " /**\n" + + " * @param blah {@inheritDoc}\n" + + " * @return {@inheritDoc}\n" + + " * @since {@inheritDoc}\n" + // error, cannot be used in @since + " * @author {@inheritDoc}\n" + // error, cannot be used in @author + " * @see {@inheritDoc}\n" + // error, cannot be used in @see + " * @throws Exception {@inheritDoc}\n" + + " * @exception Exception {@inheritDoc}\n" + + " */\n" + + " public int m(int blah) throws Exception {\n" + + " return 1;\n" + + " }\n" + + "}\n" + }, + "----------\n" + + "1. ERROR in X.java (at line 16)\n" + + " * @since {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "2. ERROR in X.java (at line 17)\n" + + " * @author {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "3. ERROR in X.java (at line 18)\n" + + " * @see {@inheritDoc}\n" + + " ^^^\n" + + "Javadoc: Missing reference\n" + + "----------\n" + + "4. ERROR in X.java (at line 18)\n" + + " * @see {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n", + JavacTestOptions.Excuse.EclipseWarningConfiguredAsError + ); +} + +// https://bugs.eclipse.org/bugs/show_bug.cgi?id=247037, make sure that we complain when @inheritdoc +// is used where it is outlawed by the specs. Test to verify that every bad use of @inheritDoc triggers +// a message from the compiler +public void testBug247037d() { + this.reportMissingJavadocTags = CompilerOptions.ERROR; + runNegativeTest( + new String[] { + "X.java", + "public class X {\n" + + "}\n" + + "class Y extends X {\n" + + " /**\n" + + " * @param blah {@inheritDoc}\n" + // error n() doesn't override anything. + " * @return {@inheritDoc}\n" + // error, n() doesn't override anything + " * @author {@inheritDoc}\n" + // error, cannot be used in @author + " */\n" + + " public int n(int blah) {\n" + + " return 1;\n" + + " }\n" + + "}\n" + }, + "----------\n" + + "1. ERROR in X.java (at line 5)\n" + + " * @param blah {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "2. ERROR in X.java (at line 6)\n" + + " * @return {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "3. ERROR in X.java (at line 7)\n" + + " * @author {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n", + JavacTestOptions.Excuse.EclipseWarningConfiguredAsError + ); +} } \ No newline at end of file Index: src/org/eclipse/jdt/core/tests/compiler/regression/JavadocTest_1_5.java =================================================================== RCS file: /cvsroot/eclipse/org.eclipse.jdt.core.tests.compiler/src/org/eclipse/jdt/core/tests/compiler/regression/JavadocTest_1_5.java,v retrieving revision 1.40 diff -u -r1.40 JavadocTest_1_5.java --- src/org/eclipse/jdt/core/tests/compiler/regression/JavadocTest_1_5.java 27 Jun 2008 16:04:44 -0000 1.40 +++ src/org/eclipse/jdt/core/tests/compiler/regression/JavadocTest_1_5.java 24 Mar 2009 05:13:18 -0000 @@ -3863,4 +3863,71 @@ JavacTestOptions.Excuse.EclipseWarningConfiguredAsError ); } + // https://bugs.eclipse.org/bugs/show_bug.cgi?id=247037, verify that we complain about @inheritDoc + // being used in package level javadoc. + public void testBug247037a() { + runNegativeTest( + new String[] { + "pack/package-info.java", + "/**\n" + + " * {@inheritDoc}\n" + + " * @since {@inheritDoc}\n" + + " * @blah {@inheritDoc}\n" + + " */\n" + + "package pack;\n" + }, + "----------\n" + + "1. ERROR in pack\\package-info.java (at line 2)\n" + + " * {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "2. ERROR in pack\\package-info.java (at line 3)\n" + + " * @since {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "3. ERROR in pack\\package-info.java (at line 4)\n" + + " * @blah {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + ); + } + + // https://bugs.eclipse.org/bugs/show_bug.cgi?id=247037, verify that we complain about @inheritDoc + // being used in package level javadoc (variation) + public void testBug247037b() { + runNegativeTest( + new String[] { + "pack/package-info.java", + "/**\n" + + " * @return {@inheritDoc}\n" + + " * @param blah {@inheritDoc}\n" + + " */\n" + + "package pack;\n" + }, + "----------\n" + + "1. ERROR in pack\\package-info.java (at line 2)\n" + + " * @return {@inheritDoc}\n" + + " ^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "2. ERROR in pack\\package-info.java (at line 2)\n" + + " * @return {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "3. ERROR in pack\\package-info.java (at line 3)\n" + + " * @param blah {@inheritDoc}\n" + + " ^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + + "4. ERROR in pack\\package-info.java (at line 3)\n" + + " * @param blah {@inheritDoc}\n" + + " ^^^^^^^^^^\n" + + "Javadoc: Unexpected tag\n" + + "----------\n" + ); + } }