Support Java 12
diff --git a/Jenkinsfile b/Jenkinsfile
index e9f05f7..9d96ed0 100644
--- a/Jenkinsfile
+++ b/Jenkinsfile
@@ -17,4 +17,4 @@
  * under the License.
  */
 
-asfMavenTlpPlgnBuild()
+asfMavenTlpPlgnBuild(jdk:['7','8','11','12'])
diff --git a/src/it/projects/MJAVADOC-325/invoker.properties b/src/it/projects/MJAVADOC-325/invoker.properties
index a4e250d..abb74d6 100644
--- a/src/it/projects/MJAVADOC-325/invoker.properties
+++ b/src/it/projects/MJAVADOC-325/invoker.properties
@@ -16,3 +16,7 @@
 # under the License.

 

 invoker.goals=clean javadoc:javadoc

+# Javadoc 12+ fails: 

+# The code being documented uses modules but the packages defined in https://docs.oracle.com/javase/1.5.0/docs/api/ are in the unnamed module.

+# Unrelated to the issue

+invoker.java.version= 12-
\ No newline at end of file
diff --git a/src/it/projects/MJAVADOC-384/pom.xml b/src/it/projects/MJAVADOC-384/pom.xml
index bedcdef..1ee0f3f 100644
--- a/src/it/projects/MJAVADOC-384/pom.xml
+++ b/src/it/projects/MJAVADOC-384/pom.xml
@@ -36,11 +36,7 @@
         <plugin>
           <groupId>org.apache.maven.plugins</groupId>
           <artifactId>maven-compiler-plugin</artifactId>
-          <version>2.3.2</version>
-          <configuration>
-            <source>1.6</source>
-            <target>1.6</target>
-          </configuration>
+          <version>3.8.0</version>
         </plugin>
         <plugin>
           <groupId>org.apache.maven.plugins</groupId>
diff --git a/src/it/projects/MJAVADOC-407/pom.xml b/src/it/projects/MJAVADOC-407/pom.xml
index a290acd..289fad0 100644
--- a/src/it/projects/MJAVADOC-407/pom.xml
+++ b/src/it/projects/MJAVADOC-407/pom.xml
@@ -36,11 +36,7 @@
         <plugin>

           <groupId>org.apache.maven.plugins</groupId>

           <artifactId>maven-compiler-plugin</artifactId>

-          <version>2.3.2</version>

-          <configuration>

-            <source>1.6</source>

-            <target>1.6</target>

-          </configuration>

+          <version>3.8.0</version>

         </plugin>

         <plugin>

           <groupId>org.apache.maven.plugins</groupId>

diff --git a/src/it/projects/MJAVADOC-562_release/invoker.properties b/src/it/projects/MJAVADOC-562_release/invoker.properties
index 9511718..13b4af8 100644
--- a/src/it/projects/MJAVADOC-562_release/invoker.properties
+++ b/src/it/projects/MJAVADOC-562_release/invoker.properties
@@ -15,4 +15,6 @@
 # specific language governing permissions and limitations
 # under the License.
 
-invoker.java.version = 9+
+# Java 9 does introduce release flag, but doesn't have proper modularized javadocs, resulting in an error:
+# The code being documented uses modules but the packages defined in https://docs.oracle.com/javase/9/docs/api/ are in the unnamed module. 
+invoker.java.version = 10+
diff --git a/src/it/projects/MJAVADOC-562_release/pom.xml b/src/it/projects/MJAVADOC-562_release/pom.xml
index 7ea691c..1e43fa8 100644
--- a/src/it/projects/MJAVADOC-562_release/pom.xml
+++ b/src/it/projects/MJAVADOC-562_release/pom.xml
@@ -31,7 +31,7 @@
 
   <properties>
     <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
-    <maven.compiler.release>9</maven.compiler.release>
+    <maven.compiler.release>10</maven.compiler.release>
   </properties>
 
   <build>
diff --git a/src/main/java/org/apache/maven/plugins/javadoc/AbstractJavadocMojo.java b/src/main/java/org/apache/maven/plugins/javadoc/AbstractJavadocMojo.java
index 189604a..17588d0 100644
--- a/src/main/java/org/apache/maven/plugins/javadoc/AbstractJavadocMojo.java
+++ b/src/main/java/org/apache/maven/plugins/javadoc/AbstractJavadocMojo.java
@@ -6099,16 +6099,20 @@
         OfflineLink link = new OfflineLink();

         link.setLocation( javaApiListFile.getParent().toAbsolutePath().toString() );

         link.setUrl( javaApiLink );

-

-        try ( InputStream in = this.getClass().getResourceAsStream( resourceName ) )

+        

+        InputStream in = this.getClass().getResourceAsStream( resourceName );

+        if ( in != null )

         {

-            // TODO only copy when changed

-            Files.copy( in, javaApiListFile, StandardCopyOption.REPLACE_EXISTING );

-        }

-        catch ( IOException ioe )

-        {

-            logError( "Can't get " + resourceName + ": " + ioe.getMessage(), ioe );

-            return null;

+            try ( InputStream closableIS = in )

+            {

+                // TODO only copy when changed

+                Files.copy( closableIS, javaApiListFile, StandardCopyOption.REPLACE_EXISTING );

+            }

+            catch ( IOException ioe )

+            {

+                logError( "Can't get " + resourceName + ": " + ioe.getMessage(), ioe );

+                return null;

+            }

         }

 

         return link;

diff --git a/src/test/java/org/apache/maven/plugins/javadoc/FixJavadocMojoTest.java b/src/test/java/org/apache/maven/plugins/javadoc/FixJavadocMojoTest.java
index 7fbb13f..e4fc2be 100644
--- a/src/test/java/org/apache/maven/plugins/javadoc/FixJavadocMojoTest.java
+++ b/src/test/java/org/apache/maven/plugins/javadoc/FixJavadocMojoTest.java
@@ -145,7 +145,7 @@
         throws Exception

     {

         // Should be an assumption, but not supported by TestCase

-        // Java 5 not supported by Java9 anymore

+        // Java 5 not supported by Java 9 anymore

         if ( JavaVersion.JAVA_SPECIFICATION_VERSION.isAtLeast( "9" ) )

         {

             return;

@@ -162,6 +162,13 @@
     public void testFixJdk6()

         throws Exception

     {

+        // Should be an assumption, but not supported by TestCase

+        // Java 6 not supported by Java 12 anymore

+        if ( JavaVersion.JAVA_SPECIFICATION_VERSION.isAtLeast( "12" ) )

+        {

+            return;

+        }

+        

         File testPomBasedir = new File( getBasedir(), "target/test/unit/fix-jdk6-test" );

         executeMojoAndTest( testPomBasedir, new String[] { "ClassWithJavadoc.java", "InterfaceWithJavadoc.java" } );

     }

@@ -643,8 +650,13 @@
         File invokerLogFile = FileUtils.createTempFile( "FixJavadocMojoTest", ".txt", invokerDir );

         

         Properties properties = new Properties();

-        

-        if( JavaVersion.JAVA_SPECIFICATION_VERSION.isAtLeast( "9" ) )

+

+        if ( JavaVersion.JAVA_SPECIFICATION_VERSION.isAtLeast( "12" ) )

+        {

+            properties.put( "maven.compiler.source", "1.7" );

+            properties.put( "maven.compiler.target", "1.7" );

+        }

+        else if ( JavaVersion.JAVA_SPECIFICATION_VERSION.isAtLeast( "9" ) )

         {

             properties.put( "maven.compiler.source", "1.6" );

             properties.put( "maven.compiler.target", "1.6" );

diff --git a/src/test/java/org/apache/maven/plugins/javadoc/JavadocReportTest.java b/src/test/java/org/apache/maven/plugins/javadoc/JavadocReportTest.java
index 0f2cec2..4716434 100644
--- a/src/test/java/org/apache/maven/plugins/javadoc/JavadocReportTest.java
+++ b/src/test/java/org/apache/maven/plugins/javadoc/JavadocReportTest.java
@@ -394,7 +394,14 @@
         assertTrue( str.toUpperCase().contains( "SAMPLE BOTTOM CONTENT" ) );

 

         // offlineLinks

-        assertTrue( str.toLowerCase().contains( "href=\"http://java.sun.com/j2se/1.4.2/docs/api/java/lang/string.html" ) );

+        if ( JavaVersion.JAVA_SPECIFICATION_VERSION.isBefore( "12" ) )

+        {

+            assertTrue( str.toLowerCase().contains( "href=\"http://java.sun.com/j2se/1.4.2/docs/api/java/lang/string.html" ) );

+        }

+        else

+        {

+            assertTrue( str.toLowerCase().contains( "href=\"http://java.sun.com/j2se/1.4.2/docs/api/java.base/java/lang/string.html" ) );

+        }

 

         // header

         assertTrue( str.toUpperCase().contains( "MAVEN JAVADOC PLUGIN TEST" ) );

@@ -734,7 +741,7 @@
         assertTrue( content.contains( "<img src=\"doc-files/maven-feather.png\" alt=\"Maven\">" ) );

 

         JavaVersion javadocVersion = (JavaVersion) getVariableValueFromObject( mojo, "javadocRuntimeVersion" );

-        if( javadocVersion.isAtLeast( "1.8" ) && javadocVersion.isBefore( "12" ) )

+        if( javadocVersion.isAtLeast( "1.8" ) && javadocVersion.isBefore( "13" ) )

         {

             // https://bugs.openjdk.java.net/browse/JDK-8032205

             assertTrue( "Javadoc runtime version: " + javadocVersion

@@ -849,6 +856,13 @@
     public void testJdk6()

         throws Exception

     {

+        // Should be an assumption, but not supported by TestCase

+        // Java 6 not supported by Java 12 anymore

+        if ( JavaVersion.JAVA_SPECIFICATION_VERSION.isAtLeast( "12" ) )

+        {

+            return;

+        }

+        

         File testPom = new File( unit, "jdk6-test/jdk6-test-plugin-config.xml" );

         JavadocReport mojo = lookupMojo( testPom );

         mojo.execute();

diff --git a/src/test/resources/unit/custom-configuration/element-list b/src/test/resources/unit/custom-configuration/element-list
new file mode 100644
index 0000000..bfb4f01
--- /dev/null
+++ b/src/test/resources/unit/custom-configuration/element-list
@@ -0,0 +1,282 @@
+module:java.base
+java.io
+java.lang
+java.lang.annotation
+java.lang.invoke
+java.lang.module
+java.lang.ref
+java.lang.reflect
+java.math
+java.net
+java.net.spi
+java.nio
+java.nio.channels
+java.nio.channels.spi
+java.nio.charset
+java.nio.charset.spi
+java.nio.file
+java.nio.file.attribute
+java.nio.file.spi
+java.security
+java.security.acl
+java.security.cert
+java.security.interfaces
+java.security.spec
+java.text
+java.text.spi
+java.time
+java.time.chrono
+java.time.format
+java.time.temporal
+java.time.zone
+java.util
+java.util.concurrent
+java.util.concurrent.atomic
+java.util.concurrent.locks
+java.util.function
+java.util.jar
+java.util.regex
+java.util.spi
+java.util.stream
+java.util.zip
+javax.crypto
+javax.crypto.interfaces
+javax.crypto.spec
+javax.net
+javax.net.ssl
+javax.security.auth
+javax.security.auth.callback
+javax.security.auth.login
+javax.security.auth.spi
+javax.security.auth.x500
+javax.security.cert
+module:java.compiler
+javax.annotation.processing
+javax.lang.model
+javax.lang.model.element
+javax.lang.model.type
+javax.lang.model.util
+javax.tools
+module:java.datatransfer
+java.awt.datatransfer
+module:java.desktop
+java.applet
+java.awt
+java.awt.color
+java.awt.desktop
+java.awt.dnd
+java.awt.event
+java.awt.font
+java.awt.geom
+java.awt.im
+java.awt.im.spi
+java.awt.image
+java.awt.image.renderable
+java.awt.print
+java.beans
+java.beans.beancontext
+javax.accessibility
+javax.imageio
+javax.imageio.event
+javax.imageio.metadata
+javax.imageio.plugins.bmp
+javax.imageio.plugins.jpeg
+javax.imageio.plugins.tiff
+javax.imageio.spi
+javax.imageio.stream
+javax.print
+javax.print.attribute
+javax.print.attribute.standard
+javax.print.event
+javax.sound.midi
+javax.sound.midi.spi
+javax.sound.sampled
+javax.sound.sampled.spi
+javax.swing
+javax.swing.border
+javax.swing.colorchooser
+javax.swing.event
+javax.swing.filechooser
+javax.swing.plaf
+javax.swing.plaf.basic
+javax.swing.plaf.metal
+javax.swing.plaf.multi
+javax.swing.plaf.nimbus
+javax.swing.plaf.synth
+javax.swing.table
+javax.swing.text
+javax.swing.text.html
+javax.swing.text.html.parser
+javax.swing.text.rtf
+javax.swing.tree
+javax.swing.undo
+module:java.instrument
+java.lang.instrument
+module:java.logging
+java.util.logging
+module:java.management
+java.lang.management
+javax.management
+javax.management.loading
+javax.management.modelmbean
+javax.management.monitor
+javax.management.openmbean
+javax.management.relation
+javax.management.remote
+javax.management.timer
+module:java.management.rmi
+javax.management.remote.rmi
+module:java.naming
+javax.naming
+javax.naming.directory
+javax.naming.event
+javax.naming.ldap
+javax.naming.spi
+module:java.net.http
+java.net.http
+module:java.prefs
+java.util.prefs
+module:java.rmi
+java.rmi
+java.rmi.activation
+java.rmi.dgc
+java.rmi.registry
+java.rmi.server
+javax.rmi.ssl
+module:java.scripting
+javax.script
+module:java.se
+module:java.security.jgss
+javax.security.auth.kerberos
+org.ietf.jgss
+module:java.security.sasl
+javax.security.sasl
+module:java.smartcardio
+javax.smartcardio
+module:java.sql
+java.sql
+javax.sql
+module:java.sql.rowset
+javax.sql.rowset
+javax.sql.rowset.serial
+javax.sql.rowset.spi
+module:java.transaction.xa
+javax.transaction.xa
+module:java.xml
+javax.xml
+javax.xml.catalog
+javax.xml.datatype
+javax.xml.namespace
+javax.xml.parsers
+javax.xml.stream
+javax.xml.stream.events
+javax.xml.stream.util
+javax.xml.transform
+javax.xml.transform.dom
+javax.xml.transform.sax
+javax.xml.transform.stax
+javax.xml.transform.stream
+javax.xml.validation
+javax.xml.xpath
+org.w3c.dom
+org.w3c.dom.bootstrap
+org.w3c.dom.events
+org.w3c.dom.ls
+org.w3c.dom.ranges
+org.w3c.dom.traversal
+org.w3c.dom.views
+org.xml.sax
+org.xml.sax.ext
+org.xml.sax.helpers
+module:java.xml.crypto
+javax.xml.crypto
+javax.xml.crypto.dom
+javax.xml.crypto.dsig
+javax.xml.crypto.dsig.dom
+javax.xml.crypto.dsig.keyinfo
+javax.xml.crypto.dsig.spec
+module:jdk.accessibility
+com.sun.java.accessibility.util
+module:jdk.attach
+com.sun.tools.attach
+com.sun.tools.attach.spi
+module:jdk.charsets
+module:jdk.compiler
+com.sun.source.doctree
+com.sun.source.tree
+com.sun.source.util
+com.sun.tools.javac
+module:jdk.crypto.cryptoki
+module:jdk.crypto.ec
+module:jdk.dynalink
+jdk.dynalink
+jdk.dynalink.beans
+jdk.dynalink.linker
+jdk.dynalink.linker.support
+jdk.dynalink.support
+module:jdk.editpad
+module:jdk.hotspot.agent
+module:jdk.httpserver
+com.sun.net.httpserver
+com.sun.net.httpserver.spi
+module:jdk.jartool
+com.sun.jarsigner
+jdk.security.jarsigner
+module:jdk.javadoc
+com.sun.javadoc
+com.sun.tools.javadoc
+jdk.javadoc.doclet
+module:jdk.jcmd
+module:jdk.jconsole
+com.sun.tools.jconsole
+module:jdk.jdeps
+module:jdk.jdi
+com.sun.jdi
+com.sun.jdi.connect
+com.sun.jdi.connect.spi
+com.sun.jdi.event
+com.sun.jdi.request
+module:jdk.jdwp.agent
+module:jdk.jfr
+jdk.jfr
+jdk.jfr.consumer
+module:jdk.jlink
+module:jdk.jshell
+jdk.jshell
+jdk.jshell.execution
+jdk.jshell.spi
+jdk.jshell.tool
+module:jdk.jsobject
+netscape.javascript
+module:jdk.jstatd
+module:jdk.localedata
+module:jdk.management
+com.sun.management
+module:jdk.management.agent
+module:jdk.management.jfr
+jdk.management.jfr
+module:jdk.naming.dns
+module:jdk.naming.rmi
+module:jdk.net
+jdk.net
+jdk.nio
+module:jdk.pack
+module:jdk.rmic
+module:jdk.scripting.nashorn
+jdk.nashorn.api.scripting
+jdk.nashorn.api.tree
+module:jdk.sctp
+com.sun.nio.sctp
+module:jdk.security.auth
+com.sun.security.auth
+com.sun.security.auth.callback
+com.sun.security.auth.login
+com.sun.security.auth.module
+module:jdk.security.jgss
+com.sun.security.jgss
+module:jdk.xml.dom
+org.w3c.dom.css
+org.w3c.dom.html
+org.w3c.dom.stylesheets
+org.w3c.dom.xpath
+module:jdk.zipfs
\ No newline at end of file