On 01/08/2014 01:00 PM, Joel Borggren-Franck wrote:
Hi Peter,

On 2014-01-03, Peter Levart wrote:
On 01/03/2014 03:52 PM, Peter Levart wrote:
This is would be all right until such proxy class
(com.sun.proxy.$Proxy1 in our example) has to access some
package-private types in some specific package. This happens in
your Named.List annotation  implementation class. It implements a
member method with the following signature:

public Named[] value() {...

...where the return type is an array of a package-private type
Named. Public class in com.sun.proxy package can not access
package-private types in other packages!
Investigating this further, I found that the declaration itself is
not problematic. It's the code in the implemented proxy method that
tries to access the package-private Named class. Here's how the
bytecode looks like for such proxy method:
... I think the error is thrown at the "checkcast" bytecode. The
improvement suggested still holds. If the proxy class was generated
in the specific package, error would not be thrown. But the
requirement to take into account all implemented interfaces and all
types encountered in the interface method signatures to calculate
the package of proxy class it too strict. Only implemented
interfaces and return types of all interface methods need to be
taken into consideration. Here's an example of bytecode that
illustrates how method parameters are passed to InvocationHandler:

Perhaps an alternative would be to check if the interface a proxy is
proxying is nested. In that case use the outermost interface's access
level for the package calculation.

This would probably lead to a few more proxies being generated into the
"real" package compared to your proposal. I don't know if that is ok or
not.

Hi Joel,

The nested public interface need not be referencing the outer class/interface. In this case, proxy class can be generated in com.sun.proxy. More importantly, even if the outer interface/class was public, the nested interface could be referencing some other package-private type. For example:


public class Outer {

    @Retention(RUNTIME)
    @interface PkgPrivate {}

    @Retention(RUNTIME)
    public @interface Public {
        PkgPrivate value();
    }


    @Public(@PkgPrivate)
    public void m() {}
}


I think the criteria for package selection should be closely tied to requirements of the generated proxy class code. And the generated code references the return type of the method.

Regards, Peter


cheers
/Joel

Reply via email to