Search in sources :

Example 1 with GetDeclaredMethodsAction

use of org.jboss.weld.security.GetDeclaredMethodsAction in project core by weld.

the class ProxyFactory method addMethods.

private void addMethods(Class<?> cls, ClassFile proxyClassType, ClassMethod staticConstructor) {
    for (Method method : AccessController.doPrivileged(new GetDeclaredMethodsAction(cls))) {
        if (isMethodAccepted(method, getProxySuperclass())) {
            try {
                MethodInformation methodInfo = new RuntimeMethodInformation(method);
                ClassMethod classMethod = proxyClassType.addMethod(method);
                addConstructedGuardToMethodBody(classMethod);
                createForwardingMethodBody(classMethod, methodInfo, staticConstructor);
                BeanLogger.LOG.addingMethodToProxy(method);
            } catch (DuplicateMemberException e) {
            // do nothing. This will happen if superclass methods
            // have been overridden
            }
        }
    }
}
Also used : DuplicateMemberException(org.jboss.classfilewriter.DuplicateMemberException) RuntimeMethodInformation(org.jboss.weld.util.bytecode.RuntimeMethodInformation) MethodInformation(org.jboss.weld.util.bytecode.MethodInformation) GetDeclaredMethodsAction(org.jboss.weld.security.GetDeclaredMethodsAction) RuntimeMethodInformation(org.jboss.weld.util.bytecode.RuntimeMethodInformation) ClassMethod(org.jboss.classfilewriter.ClassMethod) Method(java.lang.reflect.Method) ClassMethod(org.jboss.classfilewriter.ClassMethod)

Example 2 with GetDeclaredMethodsAction

use of org.jboss.weld.security.GetDeclaredMethodsAction in project core by weld.

the class InterceptedSubclassFactory method addMethodsFromClass.

@Override
protected void addMethodsFromClass(ClassFile proxyClassType, ClassMethod staticConstructor) {
    try {
        final Set<MethodSignature> finalMethods = new HashSet<MethodSignature>();
        final Set<BridgeMethod> processedBridgeMethods = new HashSet<BridgeMethod>();
        // Add all methods from the class hierarchy
        Class<?> cls = getBeanType();
        while (cls != null) {
            Set<BridgeMethod> declaredBridgeMethods = new HashSet<BridgeMethod>();
            for (Method method : AccessController.doPrivileged(new GetDeclaredMethodsAction(cls))) {
                final MethodSignatureImpl methodSignature = new MethodSignatureImpl(method);
                if (!Modifier.isFinal(method.getModifiers()) && !method.isBridge() && enhancedMethodSignatures.contains(methodSignature) && !finalMethods.contains(methodSignature) && !bridgeMethodsContainsMethod(processedBridgeMethods, methodSignature, method.getGenericReturnType(), Modifier.isAbstract(method.getModifiers()))) {
                    try {
                        final MethodInformation methodInfo = new RuntimeMethodInformation(method);
                        if (interceptedMethodSignatures.contains(methodSignature)) {
                            // create delegate-to-super method
                            createDelegateMethod(proxyClassType, method, methodInfo);
                            // this method is intercepted
                            // override a subclass method to delegate to method handler
                            ClassMethod classMethod = proxyClassType.addMethod(method);
                            addConstructedGuardToMethodBody(classMethod);
                            createForwardingMethodBody(classMethod, methodInfo, staticConstructor);
                            BeanLogger.LOG.addingMethodToProxy(method);
                        } else {
                            // this method is not intercepted
                            // we still need to override and push InterceptionDecorationContext stack to prevent full interception
                            ClassMethod classMethod = proxyClassType.addMethod(method);
                            new RunWithinInterceptionDecorationContextGenerator(classMethod, this) {

                                @Override
                                void doWork(CodeAttribute b, ClassMethod classMethod) {
                                    if (Modifier.isPrivate(classMethod.getAccessFlags())) {
                                        // Weld cannot use invokespecial to invoke a private method from the superclass
                                        invokePrivateMethodHandler(b, classMethod, methodInfo, staticConstructor);
                                    } else {
                                        // build the bytecode that invokes the super class method directly
                                        b.aload(0);
                                        // create the method invocation
                                        b.loadMethodParameters();
                                        b.invokespecial(methodInfo.getDeclaringClass(), methodInfo.getName(), methodInfo.getDescriptor());
                                    }
                                // leave the result on top of the stack
                                }

                                @Override
                                void doReturn(CodeAttribute b, ClassMethod method) {
                                    // assumes doWork() result is on top of the stack
                                    b.returnInstruction();
                                }
                            }.runStartIfNotOnTop();
                        }
                    } catch (DuplicateMemberException e) {
                    // do nothing. This will happen if superclass methods have
                    // been overridden
                    }
                } else {
                    if (Modifier.isFinal(method.getModifiers())) {
                        finalMethods.add(methodSignature);
                    }
                    if (method.isBridge()) {
                        declaredBridgeMethods.add(new BridgeMethod(methodSignature, method.getGenericReturnType()));
                    }
                }
            }
            processedBridgeMethods.addAll(declaredBridgeMethods);
            cls = cls.getSuperclass();
        }
        for (Class<?> c : getAdditionalInterfaces()) {
            for (Method method : c.getMethods()) {
                MethodSignature signature = new MethodSignatureImpl(method);
                // For interfaces we do not consider return types when going through processed bridge methods
                if (enhancedMethodSignatures.contains(signature) && !bridgeMethodsContainsMethod(processedBridgeMethods, signature, null, Modifier.isAbstract(method.getModifiers()))) {
                    try {
                        MethodInformation methodInfo = new RuntimeMethodInformation(method);
                        if (interceptedMethodSignatures.contains(signature) && Reflections.isDefault(method)) {
                            createDelegateMethod(proxyClassType, method, methodInfo);
                            // this method is intercepted
                            // override a subclass method to delegate to method handler
                            ClassMethod classMethod = proxyClassType.addMethod(method);
                            addConstructedGuardToMethodBody(classMethod);
                            createForwardingMethodBody(classMethod, methodInfo, staticConstructor);
                            BeanLogger.LOG.addingMethodToProxy(method);
                        } else {
                            if (Reflections.isDefault(method)) {
                                createDelegateMethod(proxyClassType, method, methodInfo);
                            } else {
                                final ClassMethod classMethod = proxyClassType.addMethod(method);
                                createSpecialMethodBody(classMethod, methodInfo, staticConstructor);
                                BeanLogger.LOG.addingMethodToProxy(method);
                            }
                        }
                    } catch (DuplicateMemberException e) {
                    }
                }
                if (method.isBridge()) {
                    processedBridgeMethods.add(new BridgeMethod(signature, method.getGenericReturnType()));
                }
            }
        }
    } catch (Exception e) {
        throw new WeldException(e);
    }
}
Also used : DuplicateMemberException(org.jboss.classfilewriter.DuplicateMemberException) WeldException(org.jboss.weld.exceptions.WeldException) MethodSignature(org.jboss.weld.annotated.enhanced.MethodSignature) ClassMethod(org.jboss.classfilewriter.ClassMethod) Method(java.lang.reflect.Method) WeldException(org.jboss.weld.exceptions.WeldException) DuplicateMemberException(org.jboss.classfilewriter.DuplicateMemberException) MethodSignatureImpl(org.jboss.weld.annotated.enhanced.jlr.MethodSignatureImpl) MethodInformation(org.jboss.weld.util.bytecode.MethodInformation) RuntimeMethodInformation(org.jboss.weld.util.bytecode.RuntimeMethodInformation) CodeAttribute(org.jboss.classfilewriter.code.CodeAttribute) GetDeclaredMethodsAction(org.jboss.weld.security.GetDeclaredMethodsAction) RuntimeMethodInformation(org.jboss.weld.util.bytecode.RuntimeMethodInformation) ClassMethod(org.jboss.classfilewriter.ClassMethod) HashSet(java.util.HashSet)

Example 3 with GetDeclaredMethodsAction

use of org.jboss.weld.security.GetDeclaredMethodsAction in project core by weld.

the class DecoratorProxyFactory method decoratorMethods.

private void decoratorMethods(Class<?> cls, Set<Method> all) {
    if (cls == null) {
        return;
    }
    all.addAll(Arrays.asList(AccessController.doPrivileged(new GetDeclaredMethodsAction(cls))));
    decoratorMethods(cls.getSuperclass(), all);
    // by now we should have all declared methods, let's only add the missing ones
    for (Class<?> ifc : cls.getInterfaces()) {
        Method[] methods = ifc.getMethods();
        for (Method m : methods) {
            boolean isEqual = false;
            for (Method a : all) {
                if (isEqual(m, a)) {
                    isEqual = true;
                    break;
                }
            }
            if (!isEqual) {
                all.add(m);
            }
        }
    }
}
Also used : GetDeclaredMethodsAction(org.jboss.weld.security.GetDeclaredMethodsAction) ClassMethod(org.jboss.classfilewriter.ClassMethod) Method(java.lang.reflect.Method)

Example 4 with GetDeclaredMethodsAction

use of org.jboss.weld.security.GetDeclaredMethodsAction in project core by weld.

the class InterceptedProxyFactory method addMethodsFromClass.

@Override
protected void addMethodsFromClass(ClassFile proxyClassType, ClassMethod staticConstructor) {
    try {
        final Set<MethodSignature> finalMethods = new HashSet<MethodSignature>();
        final Set<MethodSignature> processedBridgeMethods = new HashSet<MethodSignature>();
        // Add all methods from the class hierarchy
        Class<?> cls = getBeanType();
        while (cls != null) {
            Set<MethodSignature> declaredBridgeMethods = new HashSet<MethodSignature>();
            for (Method method : AccessController.doPrivileged(new GetDeclaredMethodsAction(cls))) {
                final MethodSignatureImpl methodSignature = new MethodSignatureImpl(method);
                if (isMethodAccepted(method, getProxySuperclass()) && enhancedMethodSignatures.contains(methodSignature) && !finalMethods.contains(methodSignature) && !processedBridgeMethods.contains(methodSignature)) {
                    try {
                        final MethodInformation methodInfo = new RuntimeMethodInformation(method);
                        ClassMethod classMethod = proxyClassType.addMethod(method);
                        if (interceptedMethodSignatures.contains(methodSignature)) {
                            // this method is intercepted
                            final CodeAttribute b = classMethod.getCodeAttribute();
                            b.aload(0);
                            getMethodHandlerField(classMethod.getClassFile(), b);
                            // get the Stack
                            b.invokestatic(InterceptionDecorationContext.class.getName(), "getStack", "()" + DescriptorUtils.makeDescriptor(Stack.class));
                            b.aload(0);
                            DEFAULT_METHOD_RESOLVER.getDeclaredMethod(classMethod, methodInfo.getDeclaringClass(), method.getName(), methodInfo.getParameterTypes(), staticConstructor);
                            b.dup();
                            // Params
                            b.iconst(method.getParameterTypes().length);
                            b.anewarray(JAVA_LANG_OBJECT);
                            int localVariableCount = 1;
                            for (int i = 0; i < method.getParameterTypes().length; ++i) {
                                String typeString = methodInfo.getParameterTypes()[i];
                                // duplicate the array reference
                                b.dup();
                                b.iconst(i);
                                // load the parameter value
                                BytecodeUtils.addLoadInstruction(b, typeString, localVariableCount);
                                // box the parameter if necessary
                                Boxing.boxIfNessesary(b, typeString);
                                // and store it in the array
                                b.aastore();
                                if (isWide(typeString)) {
                                    localVariableCount = localVariableCount + 2;
                                } else {
                                    localVariableCount++;
                                }
                            }
                            b.invokeinterface(StackAwareMethodHandler.class.getName(), INVOKE_METHOD_NAME, LJAVA_LANG_OBJECT, InterceptedSubclassFactory.INVOKE_METHOD_PARAMETERS);
                            if (methodInfo.getReturnType().equals(BytecodeUtils.VOID_CLASS_DESCRIPTOR)) {
                                b.returnInstruction();
                            } else if (isPrimitive(methodInfo.getReturnType())) {
                                Boxing.unbox(b, classMethod.getReturnType());
                                b.returnInstruction();
                            } else {
                                b.checkcast(BytecodeUtils.getName(methodInfo.getReturnType()));
                                b.returnInstruction();
                            }
                            BeanLogger.LOG.addingMethodToProxy(method);
                        } else {
                            final CodeAttribute b = classMethod.getCodeAttribute();
                            b.aload(0);
                            getMethodHandlerField(classMethod.getClassFile(), b);
                            b.aload(0);
                            DEFAULT_METHOD_RESOLVER.getDeclaredMethod(classMethod, methodInfo.getDeclaringClass(), method.getName(), methodInfo.getParameterTypes(), staticConstructor);
                            b.aconstNull();
                            b.iconst(method.getParameterTypes().length);
                            b.anewarray(JAVA_LANG_OBJECT);
                            int localVariableCount = 1;
                            for (int i = 0; i < method.getParameterTypes().length; ++i) {
                                String typeString = methodInfo.getParameterTypes()[i];
                                // duplicate the array reference
                                b.dup();
                                b.iconst(i);
                                // load the parameter value
                                BytecodeUtils.addLoadInstruction(b, typeString, localVariableCount);
                                // box the parameter if necessary
                                Boxing.boxIfNessesary(b, typeString);
                                // and store it in the array
                                b.aastore();
                                if (isWide(typeString)) {
                                    localVariableCount = localVariableCount + 2;
                                } else {
                                    localVariableCount++;
                                }
                            }
                            b.invokeinterface(MethodHandler.class.getName(), INVOKE_METHOD_NAME, LJAVA_LANG_OBJECT, new String[] { LJAVA_LANG_OBJECT, LJAVA_LANG_REFLECT_METHOD, LJAVA_LANG_REFLECT_METHOD, "[" + LJAVA_LANG_OBJECT });
                            if (methodInfo.getReturnType().equals(BytecodeUtils.VOID_CLASS_DESCRIPTOR)) {
                                b.returnInstruction();
                            } else if (isPrimitive(methodInfo.getReturnType())) {
                                Boxing.unbox(b, classMethod.getReturnType());
                                b.returnInstruction();
                            } else {
                                b.checkcast(BytecodeUtils.getName(methodInfo.getReturnType()));
                                b.returnInstruction();
                            }
                        }
                    } catch (DuplicateMemberException e) {
                    // do nothing. This will happen if superclass methods have
                    // been overridden
                    }
                } else {
                    if (Modifier.isFinal(method.getModifiers())) {
                        finalMethods.add(methodSignature);
                    }
                    if (method.isBridge()) {
                        declaredBridgeMethods.add(methodSignature);
                    }
                }
            }
            processedBridgeMethods.addAll(declaredBridgeMethods);
            cls = cls.getSuperclass();
        }
    } catch (Exception e) {
        throw new WeldException(e);
    }
}
Also used : DuplicateMemberException(org.jboss.classfilewriter.DuplicateMemberException) WeldException(org.jboss.weld.exceptions.WeldException) MethodSignature(org.jboss.weld.annotated.enhanced.MethodSignature) ClassMethod(org.jboss.classfilewriter.ClassMethod) Method(java.lang.reflect.Method) DuplicateMemberException(org.jboss.classfilewriter.DuplicateMemberException) WeldException(org.jboss.weld.exceptions.WeldException) MethodSignatureImpl(org.jboss.weld.annotated.enhanced.jlr.MethodSignatureImpl) MethodInformation(org.jboss.weld.util.bytecode.MethodInformation) RuntimeMethodInformation(org.jboss.weld.util.bytecode.RuntimeMethodInformation) CodeAttribute(org.jboss.classfilewriter.code.CodeAttribute) GetDeclaredMethodsAction(org.jboss.weld.security.GetDeclaredMethodsAction) RuntimeMethodInformation(org.jboss.weld.util.bytecode.RuntimeMethodInformation) ClassMethod(org.jboss.classfilewriter.ClassMethod) HashSet(java.util.HashSet)

Example 5 with GetDeclaredMethodsAction

use of org.jboss.weld.security.GetDeclaredMethodsAction in project core by weld.

the class AnnotatedTypes method createAnnotationCollectionId.

protected static String createAnnotationCollectionId(Collection<Annotation> annotations) {
    if (annotations.isEmpty()) {
        return "";
    }
    StringBuilder builder = new StringBuilder();
    builder.append('[');
    List<Annotation> annotationList = new ArrayList<Annotation>(annotations.size());
    annotationList.addAll(annotations);
    Collections.sort(annotationList, AnnotationComparator.INSTANCE);
    for (Annotation a : annotationList) {
        builder.append('@');
        builder.append(a.annotationType().getName());
        builder.append('(');
        Method[] declaredMethods = AccessController.doPrivileged(new GetDeclaredMethodsAction(a.annotationType()));
        List<Method> methods = new ArrayList<Method>(declaredMethods.length);
        Collections.addAll(methods, declaredMethods);
        Collections.sort(methods, MethodComparator.INSTANCE);
        for (int i = 0; i < methods.size(); ++i) {
            Method method = methods.get(i);
            try {
                Object value = method.invoke(a);
                builder.append(method.getName());
                builder.append('=');
                builder.append(value.toString());
            } catch (NullPointerException e) {
                throwRE(a, method, e);
            } catch (IllegalArgumentException e) {
                throwRE(a, method, e);
            } catch (IllegalAccessException e) {
                throwRE(a, method, e);
            } catch (InvocationTargetException e) {
                throwRE(a, method, e);
            }
            if (i + 1 != methods.size()) {
                builder.append(',');
            }
        }
        builder.append(')');
    }
    builder.append(']');
    return builder.toString();
}
Also used : ArrayList(java.util.ArrayList) Method(java.lang.reflect.Method) AnnotatedMethod(javax.enterprise.inject.spi.AnnotatedMethod) Annotation(java.lang.annotation.Annotation) InvocationTargetException(java.lang.reflect.InvocationTargetException) GetDeclaredMethodsAction(org.jboss.weld.security.GetDeclaredMethodsAction)

Aggregations

Method (java.lang.reflect.Method)5 GetDeclaredMethodsAction (org.jboss.weld.security.GetDeclaredMethodsAction)5 ClassMethod (org.jboss.classfilewriter.ClassMethod)4 DuplicateMemberException (org.jboss.classfilewriter.DuplicateMemberException)3 MethodInformation (org.jboss.weld.util.bytecode.MethodInformation)3 RuntimeMethodInformation (org.jboss.weld.util.bytecode.RuntimeMethodInformation)3 HashSet (java.util.HashSet)2 CodeAttribute (org.jboss.classfilewriter.code.CodeAttribute)2 MethodSignature (org.jboss.weld.annotated.enhanced.MethodSignature)2 MethodSignatureImpl (org.jboss.weld.annotated.enhanced.jlr.MethodSignatureImpl)2 WeldException (org.jboss.weld.exceptions.WeldException)2 Annotation (java.lang.annotation.Annotation)1 InvocationTargetException (java.lang.reflect.InvocationTargetException)1 ArrayList (java.util.ArrayList)1 AnnotatedMethod (javax.enterprise.inject.spi.AnnotatedMethod)1