Uploaded image for project: 'Groovy'
  1. Groovy
  2. GROOVY-6357

Inner classes in Groovy should have the same access modifiers as in Java

    XMLWordPrintableJSON

Details

    • Bug
    • Status: Closed
    • Major
    • Resolution: Fixed
    • 2.1.7
    • 2.1.8
    • bytecode, class generator
    • None

    Description

      There are differences in the flags/access modifiers for inner classes between Java and Groovy.

      Java code:

      public class Java {
                    class InnerPackage { }
          public    class InnerPublic { }
          protected class InnerProtected { }
          private   class InnerPrivate { }
      }
      

      Groovy code:

      import groovy.transform.PackageScope
      
      class Groovy {
          @PackageScope class InnerPackage { }
          public        class InnerPublic { }
          protected     class InnerProtected { }
          private       class InnerPrivate { }
      }
      

      Flags for inner classes (extracted via javap):

        package scope public scope protected scope private scope
      Java ACC_SUPER ACC_SUPER, ACC_PUBLIC ACC_SUPER, ACC_PUBLIC ACC_SUPER
      Groovy ACC_SUPER ACC_SUPER, ACC_PUBLIC ACC_SUPER, 0x4 (means ACC_PROTECTED) ACC_SUPER, 0x2 (means ACC_PRIVATE)

      Comment from blackdrag:

      I think as Groovy does is correct. But we did learn only recently, that
      the VMs have trouble doing it like this. AS a result we forbid the
      private modifer on classes... but looks like we forgot inner classes.

      These different flags for example result in Cobertura failing to instrument the inner classes because ASM throws this exception:

      Unable to instrument file build/instrumented_classes/Groovy$InnerPrivate.class
      java.lang.IllegalArgumentException: Invalid access flags: 34
              at org.objectweb.asm.util.CheckClassAdapter.checkAccess(Unknown Source)
              at org.objectweb.asm.util.CheckClassAdapter.visit(Unknown Source)
              at org.objectweb.asm.ClassVisitor.visit(Unknown Source)
              at net.sourceforge.cobertura.instrument.pass1.DetectDuplicatedCodeClassVisitor.visit(DetectDuplicatedCodeClassVisitor.java:205)
              at org.objectweb.asm.ClassReader.accept(Unknown Source)
              at org.objectweb.asm.ClassReader.accept(Unknown Source)
              at net.sourceforge.cobertura.instrument.CoberturaInstrumenter.instrumentClass(CoberturaInstrumenter.java:153)
              at net.sourceforge.cobertura.instrument.CoberturaInstrumenter.instrumentClass(CoberturaInstrumenter.java:121)
              at net.sourceforge.cobertura.instrument.CoberturaInstrumenter.addInstrumentationToSingleClass(CoberturaInstrumenter.java:234)
              at net.sourceforge.cobertura.instrument.Main.addInstrumentationToSingleClass(Main.java:298)
              at net.sourceforge.cobertura.instrument.Main.addInstrumentation(Main.java:307)
              at net.sourceforge.cobertura.instrument.Main.addInstrumentation(Main.java:316)
              at net.sourceforge.cobertura.instrument.Main.parseArguments(Main.java:399)
              at net.sourceforge.cobertura.instrument.Main.main(Main.java:421)
              at net.saliman.gradle.plugin.cobertura.CoberturaRunner.instrument(CoberturaRunner.java:79)
      

      Attachments

        Activity

          People

            melix Cédric Champeau
            rene.scheibe Rene Scheibe
            Votes:
            0 Vote for this issue
            Watchers:
            1 Start watching this issue

            Dates

              Created:
              Updated:
              Resolved: