Search in sources :

Example 41 with GroovyBugError

use of org.codehaus.groovy.GroovyBugError in project groovy-core by groovy.

the class StaticTypeCheckingSupport method evaluateExpression.

/**
     * A helper method that can be used to evaluate expressions as found in annotation
     * parameters. For example, it will evaluate a constant, be it referenced directly as
     * an integer or as a reference to a field.
     *
     * If this method throws an exception, then the expression cannot be evaluated on its own.
     *
     * @param expr the expression to be evaluated
     * @param config the compiler configuration
     * @return the result of the expression
     */
public static Object evaluateExpression(Expression expr, CompilerConfiguration config) {
    String className = "Expression$" + UUID.randomUUID().toString().replace('-', '$');
    ClassNode node = new ClassNode(className, Opcodes.ACC_PUBLIC, ClassHelper.OBJECT_TYPE);
    ReturnStatement code = new ReturnStatement(expr);
    node.addMethod(new MethodNode("eval", Opcodes.ACC_PUBLIC + Opcodes.ACC_STATIC, ClassHelper.OBJECT_TYPE, Parameter.EMPTY_ARRAY, ClassNode.EMPTY_ARRAY, code));
    CompilerConfiguration copyConf = new CompilerConfiguration(config);
    CompilationUnit cu = new CompilationUnit(copyConf);
    cu.addClassNode(node);
    cu.compile(Phases.CLASS_GENERATION);
    @SuppressWarnings("unchecked") List<GroovyClass> classes = (List<GroovyClass>) cu.getClasses();
    Class aClass = cu.getClassLoader().defineClass(className, classes.get(0).getBytes());
    try {
        return aClass.getMethod("eval").invoke(null);
    } catch (IllegalAccessException e) {
        throw new GroovyBugError(e);
    } catch (InvocationTargetException e) {
        throw new GroovyBugError(e);
    } catch (NoSuchMethodException e) {
        throw new GroovyBugError(e);
    }
}
Also used : CompilationUnit(org.codehaus.groovy.control.CompilationUnit) GroovyClass(org.codehaus.groovy.tools.GroovyClass) GroovyBugError(org.codehaus.groovy.GroovyBugError) InvocationTargetException(java.lang.reflect.InvocationTargetException) ReturnStatement(org.codehaus.groovy.ast.stmt.ReturnStatement) CompilerConfiguration(org.codehaus.groovy.control.CompilerConfiguration) GroovyClass(org.codehaus.groovy.tools.GroovyClass)

Example 42 with GroovyBugError

use of org.codehaus.groovy.GroovyBugError in project groovy-core by groovy.

the class StaticTypeCheckingVisitor method extractPlaceHolders.

private static Map<String, GenericsType> extractPlaceHolders(MethodNode method, ClassNode receiver, ClassNode declaringClass) {
    if (declaringClass.equals(OBJECT_TYPE)) {
        Map<String, GenericsType> resolvedPlaceholders = new HashMap<String, GenericsType>();
        if (method != null)
            addMethodLevelDeclaredGenerics(method, resolvedPlaceholders);
        return resolvedPlaceholders;
    }
    Map<String, GenericsType> resolvedPlaceholders = null;
    if (isPrimitiveType(receiver) && !isPrimitiveType(declaringClass)) {
        receiver = getWrapper(receiver);
    }
    final List<ClassNode> queue;
    if (receiver instanceof UnionTypeClassNode) {
        queue = Arrays.asList(((UnionTypeClassNode) receiver).getDelegates());
    } else {
        queue = Collections.singletonList(receiver);
    }
    for (ClassNode item : queue) {
        ClassNode current = item;
        while (current != null) {
            boolean continueLoop = true;
            //extract the place holders
            Map<String, GenericsType> currentPlaceHolders = new HashMap<String, GenericsType>();
            if (isGenericsPlaceHolderOrArrayOf(declaringClass) || declaringClass.equals(current)) {
                extractGenericsConnections(currentPlaceHolders, current, declaringClass);
                if (method != null)
                    addMethodLevelDeclaredGenerics(method, currentPlaceHolders);
                continueLoop = false;
            } else {
                GenericsUtils.extractPlaceholders(current, currentPlaceHolders);
            }
            if (resolvedPlaceholders != null) {
                // merge maps
                Set<Map.Entry<String, GenericsType>> entries = currentPlaceHolders.entrySet();
                for (Map.Entry<String, GenericsType> entry : entries) {
                    GenericsType gt = entry.getValue();
                    if (!gt.isPlaceholder())
                        continue;
                    GenericsType referenced = resolvedPlaceholders.get(gt.getName());
                    if (referenced == null)
                        continue;
                    entry.setValue(referenced);
                }
            }
            resolvedPlaceholders = currentPlaceHolders;
            // we are done if we are now in the declaring class
            if (!continueLoop)
                break;
            current = getNextSuperClass(current, declaringClass);
            if (current == null && CLASS_Type.equals(declaringClass)) {
                // this can happen if the receiver is Class<Foo>, then
                // the actual receiver is Foo and declaringClass is Class
                current = declaringClass;
            }
        }
    }
    if (resolvedPlaceholders == null) {
        String descriptor = "<>";
        if (method != null)
            descriptor = method.getTypeDescriptor();
        throw new GroovyBugError("Declaring class for method call to '" + descriptor + "' declared in " + declaringClass.getName() + " was not matched with found receiver " + receiver.getName() + "." + " This should not have happened!");
    }
    return resolvedPlaceholders;
}
Also used : LowestUpperBoundClassNode(org.codehaus.groovy.ast.tools.WideningCategories.LowestUpperBoundClassNode) ClassNode(org.codehaus.groovy.ast.ClassNode) InnerClassNode(org.codehaus.groovy.ast.InnerClassNode) LinkedHashMap(java.util.LinkedHashMap) ListHashMap(org.codehaus.groovy.util.ListHashMap) HashMap(java.util.HashMap) GroovyBugError(org.codehaus.groovy.GroovyBugError) GenericsType(org.codehaus.groovy.ast.GenericsType) Map(java.util.Map) LinkedHashMap(java.util.LinkedHashMap) ListHashMap(org.codehaus.groovy.util.ListHashMap) HashMap(java.util.HashMap)

Example 43 with GroovyBugError

use of org.codehaus.groovy.GroovyBugError in project groovy-core by groovy.

the class GeneratorContext method encodeAsValidClassName.

public static String encodeAsValidClassName(String name) {
    final int l = name.length();
    StringBuilder b = null;
    int lastEscape = -1;
    for (int i = 0; i < l; ++i) {
        final int encodeIndex = name.charAt(i) - MIN_ENCODING;
        if (encodeIndex >= 0 && encodeIndex < CHARACTERS_TO_ENCODE.length) {
            if (CHARACTERS_TO_ENCODE[encodeIndex]) {
                if (b == null) {
                    b = new StringBuilder(name.length() + 3);
                    b.append(name, 0, i);
                } else {
                    b.append(name, lastEscape + 1, i);
                }
                b.append('_');
                lastEscape = i;
            }
        }
    }
    if (b == null)
        return name.toString();
    if (lastEscape == -1)
        throw new GroovyBugError("unexpected escape char control flow in " + name);
    b.append(name, lastEscape + 1, l);
    return b.toString();
}
Also used : GroovyBugError(org.codehaus.groovy.GroovyBugError)

Example 44 with GroovyBugError

use of org.codehaus.groovy.GroovyBugError in project groovy-core by groovy.

the class AsmClassGenerator method visitAnnotationDefaultExpression.

void visitAnnotationDefaultExpression(AnnotationVisitor av, ClassNode type, Expression exp) {
    if (exp instanceof ClosureExpression) {
        ClassNode closureClass = controller.getClosureWriter().getOrAddClosureClass((ClosureExpression) exp, ACC_PUBLIC);
        Type t = Type.getType(BytecodeHelper.getTypeDescription(closureClass));
        av.visit(null, t);
    } else if (type.isArray()) {
        ListExpression list = (ListExpression) exp;
        AnnotationVisitor avl = av.visitArray(null);
        ClassNode componentType = type.getComponentType();
        for (Expression lExp : list.getExpressions()) {
            visitAnnotationDefaultExpression(avl, componentType, lExp);
        }
    } else if (ClassHelper.isPrimitiveType(type) || type.equals(ClassHelper.STRING_TYPE)) {
        ConstantExpression constExp = (ConstantExpression) exp;
        av.visit(null, constExp.getValue());
    } else if (ClassHelper.CLASS_Type.equals(type)) {
        ClassNode clazz = exp.getType();
        Type t = Type.getType(BytecodeHelper.getTypeDescription(clazz));
        av.visit(null, t);
    } else if (type.isDerivedFrom(ClassHelper.Enum_Type)) {
        PropertyExpression pExp = (PropertyExpression) exp;
        ClassExpression cExp = (ClassExpression) pExp.getObjectExpression();
        String desc = BytecodeHelper.getTypeDescription(cExp.getType());
        String name = pExp.getPropertyAsString();
        av.visitEnum(null, desc, name);
    } else if (type.implementsInterface(ClassHelper.Annotation_TYPE)) {
        AnnotationConstantExpression avExp = (AnnotationConstantExpression) exp;
        AnnotationNode value = (AnnotationNode) avExp.getValue();
        AnnotationVisitor avc = av.visitAnnotation(null, BytecodeHelper.getTypeDescription(avExp.getType()));
        visitAnnotationAttributes(value, avc);
    } else {
        throw new GroovyBugError("unexpected annotation type " + type.getName());
    }
    av.visitEnd();
}
Also used : InnerClassNode(org.codehaus.groovy.ast.InnerClassNode) InterfaceHelperClassNode(org.codehaus.groovy.ast.InterfaceHelperClassNode) ClassNode(org.codehaus.groovy.ast.ClassNode) GroovyBugError(org.codehaus.groovy.GroovyBugError) Type(org.objectweb.asm.Type) GenericsType(org.codehaus.groovy.ast.GenericsType) AnnotationNode(org.codehaus.groovy.ast.AnnotationNode) AnnotationVisitor(org.objectweb.asm.AnnotationVisitor)

Example 45 with GroovyBugError

use of org.codehaus.groovy.GroovyBugError in project groovy-core by groovy.

the class Expression method transformExpressions.

/**
     * Transforms the list of expressions, and checks that all transformed expressions have the given type.
     *
     * @return a new list of transformed expressions
     */
protected <T extends Expression> List<T> transformExpressions(List<? extends Expression> expressions, ExpressionTransformer transformer, Class<T> transformedType) {
    List<T> list = new ArrayList<T>(expressions.size());
    for (Expression expr : expressions) {
        Expression transformed = transformer.transform(expr);
        if (!transformedType.isInstance(transformed))
            throw new GroovyBugError(String.format("Transformed expression should have type %s but has type %s", transformedType, transformed.getClass()));
        list.add(transformedType.cast(transformed));
    }
    return list;
}
Also used : ArrayList(java.util.ArrayList) GroovyBugError(org.codehaus.groovy.GroovyBugError)

Aggregations

GroovyBugError (org.codehaus.groovy.GroovyBugError)71 ClassNode (org.codehaus.groovy.ast.ClassNode)31 AnnotationNode (org.codehaus.groovy.ast.AnnotationNode)11 InnerClassNode (org.codehaus.groovy.ast.InnerClassNode)11 MethodNode (org.codehaus.groovy.ast.MethodNode)11 GenericsType (org.codehaus.groovy.ast.GenericsType)9 AnnotatedNode (org.codehaus.groovy.ast.AnnotatedNode)8 FieldNode (org.codehaus.groovy.ast.FieldNode)8 SyntaxException (org.codehaus.groovy.syntax.SyntaxException)8 MethodVisitor (org.objectweb.asm.MethodVisitor)8 VariableExpression (org.codehaus.groovy.ast.expr.VariableExpression)7 Closure (groovy.lang.Closure)6 GroovyRuntimeException (groovy.lang.GroovyRuntimeException)6 IOException (java.io.IOException)6 ArrayList (java.util.ArrayList)6 LinkedList (java.util.LinkedList)5 Expression (org.codehaus.groovy.ast.expr.Expression)5 GroovyClassLoader (groovy.lang.GroovyClassLoader)4 InvocationTargetException (java.lang.reflect.InvocationTargetException)4 Collection (java.util.Collection)4