title: Loader Constraint Violation loading Antlr jar in Eclipse plugin built with Tycho
body: <p>I've been working on an Eclipse plugin codebase that builds with Maven Tycho.  I can provide some snippets that anyone asks for, but you can get the code at <a href="https://git.opendaylight.org/gerrit/#/admin/projects/yangide" rel="nofollow">https://git.opendaylight.org/gerrit/#/admin/projects/yangide</a>  (I believe that should be open).</p>
  
  <p>I usually test it with an "Eclipse Application" launch config, loading all the plugins in the workspace.  This works.</p>
  
  <p>I sometimes test it by referencing the update site zip that I build locally.  This works most of the time.</p>
  
  <p>Recently, someone else I work with has deployed the update site to a public URL (<a href="https://nexus.opendaylight.org/content/sites/p2repos/org.opendaylight.yangide" rel="nofollow">https://nexus.opendaylight.org/content/sites/p2repos/org.opendaylight.yangide</a>).  This was built from master.</p>
  
  <p>When I install from this into a standalone Eclipse, at some point after startup I see the following error:</p>
  
  <pre><code>Exception:java.lang.LinkageError: org/antlr/v4/runtime/TokenStream
   at org.antlr.v4.runtime.Parser.setInputStream(Parser.java:530)
   at org.antlr.v4.runtime.Parser.&lt;init&gt;(Parser.java:182)
   at org.opendaylight.yangtools.antlrv4.code.gen.YangParser.&lt;init&gt;(YangParser.java:188)
  </code></pre>
  
  <p>I've actually seen this same exception sometimes when testing with the locally built update site zip, but rarely.  I'm seeing it every time with this deployed update site.</p>
  
  <p>So I understand that "Linkage Error" means that the class had already been loaded by another classloader which conflicts with this.</p>
  
  <p>So, I started it up again with "-verbose:class" to at least see some information about the loading of this class.</p>
  
  <p>From this output, I saw the following:</p>
  
  <pre><code>[Loaded org.antlr.v4.runtime.TokenStream from file:/home/opnfv/frameworks/eclipse-neon/java-mars/eclipse/../../../../.p2/pool/plugins/net.sf.eclipsecs.checkstyle_6.16.0.201603042321/checkstyle-6.16.1-all.jar]
  [Loaded org.antlr.v4.runtime.TokenStream from file:/home/opnfv/frameworks/eclipse-neon/java-mars/eclipse/configuration/org.eclipse.osgi/605/0/.cp/libs/antlr4-runtime-4.5.1.jar]
  [Loaded org.antlr.v4.runtime.TokenStream from file:/home/opnfv/.m2/repository/org/antlr/antlr4-runtime/4.5.1/antlr4-runtime-4.5.1.jar]
  </code></pre>
  
  <p>Note that this plugin obtains several jars from a Maven repo, as opposed to a p2 repo, including the "antlr4-runtime-4.5.1.jar" file.  Most of these jars are not available in a public p2 repo.  One of the plugins uses the "copy" and "copy-dependencies" goals of the "maven-dependency-plugin" to get Maven artifacts, and then specifies the local paths to those jars in the "Bundle-ClassPath" property in the META-INF/MANIFEST.MF file.  other plugins in the codebase specify that plugin as a dependency.</p>
  
  <p><strong>Update</strong>:</p>
  
  <p>Note that I sometimes see the following variation of this in the log:</p>
  
  <pre><code>Exception in thread "Yang indexer" java.lang.LinkageError: loader constraint violation: loader (instance of org/eclipse/osgi/internal/loader/EquinoxClassLoader) previously initiated loading for a different type with name "org/antlr/v4/runtime/TokenStream"
      at java.lang.ClassLoader.defineClass1(Native Method)
      at java.lang.ClassLoader.defineClass(ClassLoader.java:760)
      at org.eclipse.osgi.internal.loader.ModuleClassLoader.defineClass(ModuleClassLoader.java:272)
      at org.eclipse.osgi.internal.loader.classpath.ClasspathManager.defineClass(ClasspathManager.java:632)
      at org.eclipse.osgi.internal.loader.classpath.ClasspathManager.findClassImpl(ClasspathManager.java:588)
      at org.eclipse.osgi.internal.loader.classpath.ClasspathManager.findLocalClassImpl(ClasspathManager.java:540)
      at org.eclipse.osgi.internal.loader.classpath.ClasspathManager.findLocalClass(ClasspathManager.java:527)
      at org.eclipse.osgi.internal.loader.ModuleClassLoader.findLocalClass(ModuleClassLoader.java:324)
      at org.eclipse.osgi.internal.loader.BundleLoader.findLocalClass(BundleLoader.java:327)
      at org.eclipse.osgi.internal.loader.BundleLoader.findClassInternal(BundleLoader.java:402)
      at org.eclipse.osgi.internal.loader.BundleLoader.findClass(BundleLoader.java:352)
      at org.eclipse.osgi.internal.loader.BundleLoader.findClass(BundleLoader.java:344)
      at org.eclipse.osgi.internal.loader.ModuleClassLoader.loadClass(ModuleClassLoader.java:160)
      at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
      at org.antlr.v4.runtime.Parser.setInputStream(Parser.java:530)
  </code></pre>
  
  <p><strong>Update</strong>:</p>
  
  <p>I realized that it might be useful to add "-verbose:class" to the launch config test case, because that is not having this problem.  When I searched for the same class reference in the output, I only saw one occurrence:</p>
  
  <pre><code>[Loaded org.antlr.v4.runtime.TokenStream from file:/home/opnfv/workspace3/.metadata/.plugins/org.eclipse.pde.core/.bundle_pool/../../../../../../../media/sf_laptophome/git/yangide/plugins/com.cisco.yangide.yangparser/libs/antlr4-runtime-4.5.1.jar]
  </code></pre>
  
  <p>Remember that this is just loading the plugins from the workspace.  This path is essentially in my workspace.  In any case, it never tried to load it from those other two jar files.</p>