All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.alibaba.fastjson2.internal.processor.JavacTreeUtils Maven / Gradle / Ivy

package com.alibaba.fastjson2.internal.processor;

import com.alibaba.fastjson2.JSONWriter;
import com.sun.source.tree.MemberReferenceTree;
import com.sun.tools.javac.code.Flags;
import com.sun.tools.javac.code.Symbol;
import com.sun.tools.javac.code.TypeTag;
import com.sun.tools.javac.processing.JavacProcessingEnvironment;
import com.sun.tools.javac.tree.JCTree;
import com.sun.tools.javac.tree.TreeMaker;
import com.sun.tools.javac.util.List;
import com.sun.tools.javac.util.ListBuffer;
import com.sun.tools.javac.util.Name;
import com.sun.tools.javac.util.Names;

import javax.annotation.processing.ProcessingEnvironment;
import javax.lang.model.element.TypeElement;
import javax.lang.model.util.Elements;

import java.lang.reflect.*;

import static com.alibaba.fastjson2.internal.processor.CodeGenUtils.JVM_VERSION;

final class JavacTreeUtils {
    private static TreeMaker treeMaker;
    private static Names names;
    private static Elements elements;

    private JavacTreeUtils() {
        throw new UnsupportedOperationException("this class can not be instantiated");
    }

    static void initialize(TreeMaker _treeMaker, Names _names, Elements _elements) {
        treeMaker = _treeMaker;
        names = _names;
        elements = _elements;
    }

    static ProcessingEnvironment unwrapProcessingEnv(ProcessingEnvironment processingEnv) {
        if (processingEnv instanceof JavacProcessingEnvironment) {
            return processingEnv;
        }
        // IntelliJ >2020.3 wraps the processing environment in a dynamic proxy.
        ProcessingEnvironment unwrappedIntelliJ = unwrapIntelliJ(processingEnv);
        if (unwrappedIntelliJ != null) {
            return unwrapProcessingEnv(unwrappedIntelliJ);
        }
        // Gradle incremental build wraps the processing environment.
        for (Class envClass = processingEnv.getClass(); envClass != null; envClass = envClass.getSuperclass()) {
            ProcessingEnvironment unwrappedGradle = unwrapGradle(envClass, processingEnv);
            if (unwrappedGradle != null) {
                return unwrapProcessingEnv(unwrappedGradle);
            }
        }
        throw new IllegalArgumentException("failed to retrieve JavacProcessingEnvironment");
    }

    private static ProcessingEnvironment unwrapIntelliJ(ProcessingEnvironment processingEnv) {
        try {
            InvocationHandler handler = Proxy.getInvocationHandler(processingEnv);
            Field field = handler.getClass().getDeclaredField("val$delegateTo");
            field.setAccessible(true);
            Object object = field.get(handler);
            if (object instanceof ProcessingEnvironment) {
                return (ProcessingEnvironment) object;
            }
        } catch (NoSuchFieldException | IllegalAccessException e) {
            // just ignore
        }
        return null;
    }

    private static ProcessingEnvironment unwrapGradle(Class delegateClass, ProcessingEnvironment processingEnv) {
        try {
            Field field = delegateClass.getDeclaredField("delegate");
            field.setAccessible(true);
            Object object = field.get(processingEnv);
            if (object instanceof ProcessingEnvironment) {
                return (ProcessingEnvironment) object;
            }
        } catch (NoSuchFieldException | IllegalAccessException e) {
            // just ignore
        }
        return null;
    }

    static JCTree.JCLiteral defNull() {
        return literal(TypeTag.BOT, null);
    }

    static Name name(String name) {
        return names.fromString(name);
    }

    static JCTree.JCIdent ident(String name) {
        return treeMaker.Ident(name(name));
    }

    static JCTree.JCIdent ident(Name name) {
        return treeMaker.Ident(name);
    }

    static JCTree.JCIdent ident(JCTree.JCVariableDecl var) {
        return treeMaker.Ident(var.name);
    }

    static JCTree.JCExpression qualIdent(Class type) {
        return qualIdent(type.getName());
    }

    static JCTree.JCExpression qualIdent(String name) {
        TypeElement typeElement = elements.getTypeElement(name);
        if (typeElement != null) {
            return treeMaker.QualIdent((Symbol) typeElement);
        } else {
            return ident(name(name));
        }
    }

    static JCTree.JCExpression arrayIdentType(String name) {
        int idx = name.indexOf("[");
        String type = name;
        int count = 1;
        if (idx != -1) {
            type = name.substring(0, idx);
            count = 0;
            for (char c : name.substring(idx).toCharArray()) {
                if (c == '[') {
                    count++;
                }
            }
        }
        return arrayType(identType(type), count);
    }

    static JCTree.JCExpression identType(String type) {
        JCTree.JCExpression identType;
        switch (type) {
            case "int":
                identType = treeMaker.TypeIdent(TypeTag.INT);
                break;
            case "long":
                identType = treeMaker.TypeIdent(TypeTag.LONG);
                break;
            case "float":
                identType = treeMaker.TypeIdent(TypeTag.FLOAT);
                break;
            case "double":
                identType = treeMaker.TypeIdent(TypeTag.DOUBLE);
                break;
            case "boolean":
                identType = treeMaker.TypeIdent(TypeTag.BOOLEAN);
                break;
            case "char":
                identType = treeMaker.TypeIdent(TypeTag.CHAR);
                break;
            case "byte":
                identType = treeMaker.TypeIdent(TypeTag.BYTE);
                break;
            case "short":
                identType = treeMaker.TypeIdent(TypeTag.SHORT);
                break;
            default:
                identType = qualIdent(type);
        }
        return identType;
    }

    static String boxed(String type) {
        String boxed = type;
        switch (type) {
            case "int":
                boxed = "Integer";
                break;
            case "long":
                boxed = "Long";
                break;
            case "float":
                boxed = "Float";
                break;
            case "double":
                boxed = "Double";
                break;
            case "boolean":
                boxed = "Boolean";
                break;
            case "char":
                boxed = "Character";
                break;
            case "byte":
                boxed = "Byte";
                break;
            case "short":
                boxed = "Short";
                break;
            default:
        }
        return boxed;
    }

    static JCTree.JCArrayTypeTree arrayType(JCTree.JCExpression elemTypeExpr, int dims) {
        if (dims == 1) {
            return treeMaker.TypeArray(elemTypeExpr);
        } else {
            return treeMaker.TypeArray(arrayType(elemTypeExpr, dims - 1));
        }
    }

    static JCTree.JCTypeApply collectionIdent(String type) {
        return collectionType(type);
    }

    private static JCTree.JCTypeApply collectionType(String type) {
        int open = type.indexOf("<");
        int close = type.indexOf(">");
        String clazz = type.substring(0, open);
        if (close == type.length() - 1) {
            String args = type.substring(open + 1, close);
            ListBuffer generics = new ListBuffer<>();
            for (String g : args.split(",")) {
                generics.append(qualIdent(g));
            }
            return typeApply(qualIdent(clazz), generics.toList());
        } else {
            return typeApply(qualIdent(clazz), List.of(collectionType(type.substring(open + 1, close + 1))));
        }
    }

    static JCTree.JCVariableDecl defVar(long flag, String identName, JCTree.JCExpression identType) {
        return defVar(flag, identName, identType, null);
    }

    static JCTree.JCVariableDecl defVar(String identName, JCTree.JCExpression identType) {
        return defVar(Flags.PARAMETER, identName, identType, null);
    }

    static JCTree.JCVariableDecl defVar(long flag, String identName, TypeTag typeTag) {
        return defVar(flag, identName, type(typeTag), null);
    }

    static JCTree.JCVariableDecl defVar(String identName, TypeTag typeTag) {
        return defVar(Flags.PARAMETER, identName, type(typeTag), null);
    }

    static JCTree.JCVariableDecl defVar(String identName, JCTree.JCExpression identType, JCTree.JCExpression init) {
        return defVar(Flags.PARAMETER, identName, identType, init);
    }

    static JCTree.JCVariableDecl defVar(Name identName, JCTree.JCExpression identType, JCTree.JCExpression init) {
        return defVar(Flags.PARAMETER, identName, identType, init);
    }

    static JCTree.JCVariableDecl defVar(long flag, Name identName, JCTree.JCExpression identType, JCTree.JCExpression init) {
        return treeMaker.VarDef(modifiers(flag), identName, identType, init);
    }

    static JCTree.JCVariableDecl defVar(long flag, String identName, JCTree.JCExpression identType, JCTree.JCExpression init) {
        return treeMaker.VarDef(modifiers(flag), name(identName), identType, init);
    }

    static JCTree.JCVariableDecl defVar(String identName, TypeTag typeTag, JCTree.JCExpression init) {
        return treeMaker.VarDef(modifiers(Flags.PARAMETER), name(identName), type(typeTag), init);
    }

    static JCTree.JCVariableDecl defVar(long flag, String identName, TypeTag typeTag, JCTree.JCExpression init) {
        return treeMaker.VarDef(modifiers(flag), name(identName), type(typeTag), init);
    }

    static JCTree.JCVariableDecl defVar(String identName, long init) {
        return defVar(Flags.PARAMETER, identName, TypeTag.LONG, literal(init));
    }

    static JCTree.JCVariableDecl defVar(String identName, int init) {
        return defVar(Flags.PARAMETER, identName, TypeTag.INT, literal(init));
    }

    static JCTree.JCVariableDecl defVar(long flag, String identName, long init) {
        return treeMaker.VarDef(modifiers(flag), name(identName), type(TypeTag.LONG), literal(init));
    }

    static JCTree.JCVariableDecl defVar(long flag, String identName, int init) {
        return treeMaker.VarDef(modifiers(flag), name(identName), type(TypeTag.INT), literal(init));
    }

    static JCTree.JCVariableDecl defVar(String identName, boolean init) {
        return defVar(Flags.PARAMETER, identName, init);
    }

    static JCTree.JCVariableDecl defVar(long flag, String identName, boolean init) {
        return treeMaker.VarDef(modifiers(flag), name(identName), type(TypeTag.BOOLEAN), literal(init));
    }

    static JCTree.JCMethodDecl defMethod(
            long flag,
            String name,
            JCTree.JCExpression rtnType,
            List params,
            JCTree.JCBlock block
    ) {
        return defMethod(flag, name(name), rtnType, null, params, null, block, null);
    }

    static JCTree.JCMethodDecl defMethod(
            long flag,
            String name,
            JCTree.JCExpression rtnType,
            List typeArgs,
            List params,
            List recvArgs,
            JCTree.JCBlock block,
            JCTree.JCExpression defaultValue
    ) {
        return defMethod(flag, name(name), rtnType, typeArgs, params, recvArgs, block, defaultValue);
    }

    static JCTree.JCMethodDecl defMethod(
            long flag,
            Name name,
            JCTree.JCExpression rtnType,
            List typeArgs,
            List params,
            List recvArgs,
            JCTree.JCBlock block,
            JCTree.JCExpression defaultValue
    ) {
        if (typeArgs == null) {
            typeArgs = List.nil();
        }
        if (params == null) {
            params = List.nil();
        }
        if (recvArgs == null) {
            recvArgs = List.nil();
        }
        return treeMaker.MethodDef(modifiers(flag), name, rtnType, typeArgs, params, recvArgs, block, defaultValue);
    }

    static JCTree.JCMethodInvocation method(JCTree.JCExpression method) {
        return method(null, method, null);
    }

    static JCTree.JCMethodInvocation method(JCTree.JCExpression method, List args) {
        return method(null, method, args);
    }

    static JCTree.JCMethodInvocation method(JCTree.JCExpression owner, String methodName, List args) {
        return method(null, field(owner, methodName), args);
    }

    static JCTree.JCMethodInvocation method(JCTree.JCExpression method, JCTree.JCExpression arg0) {
        return method(null, method, List.of(arg0));
    }

    static JCTree.JCMethodInvocation method(JCTree.JCExpression method, JCTree.JCExpression arg0, JCTree.JCExpression arg1, JCTree.JCExpression arg2) {
        return method(null, method, List.of(arg0, arg1, arg2));
    }

    static JCTree.JCMethodInvocation method(Name owner, String methodName, List args) {
        return method(null, field(ident(owner), methodName), args);
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCExpression owner,
            String methodName
    ) {
        return method(null, field(owner, methodName), null);
    }

    static JCTree.JCMethodInvocation method(
            Name owner,
            String methodName
    ) {
        return method(null, field(ident(owner), methodName), null);
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCVariableDecl owner,
            String methodName
    ) {
        return method(null, field(ident(owner), methodName), null);
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner, String methodName
    ) {
        return method(null, field(owner, methodName), null);
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCExpression owner,
            String methodName,
            JCTree.JCExpression arg0
    ) {
        return method(null, field(owner, methodName), List.of(arg0));
    }

    static JCTree.JCMethodInvocation method(
            Name owner,
            String methodName,
            JCTree.JCExpression arg0
    ) {
        return method(null, field(ident(owner), methodName), List.of(arg0));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCVariableDecl owner,
            String methodName,
            JCTree.JCExpression arg0
    ) {
        return method(null, field(ident(owner), methodName), List.of(arg0));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            JCTree.JCExpression arg0
    ) {
        return method(null, field(owner, methodName), List.of(arg0));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            String arg0
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            JCTree.JCVariableDecl arg0
    ) {
        return method(null, field(owner, methodName), List.of(ident(arg0)));
    }

    static JCTree.JCMethodInvocation method(
            Name owner,
            String methodName,
            JCTree.JCExpression arg0,
            JCTree.JCExpression arg1
    ) {
        return method(null, field(ident(owner), methodName), List.of(arg0, arg1));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCExpression owner,
            String methodName,
            JCTree.JCExpression arg0,
            JCTree.JCExpression arg1
    ) {
        return method(null, field(owner, methodName), List.of(arg0, arg1));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCExpression owner,
            String methodName,
            JCTree.JCExpression arg0,
            JCTree.JCVariableDecl arg1
    ) {
        return method(null, field(owner, methodName), List.of(arg0, ident(arg1)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            JCTree.JCExpression arg0,
            JCTree.JCExpression arg1
    ) {
        return method(null, field(owner, methodName), List.of(arg0, arg1));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            int arg1
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            int arg1,
            byte arg2
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            byte arg2
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            int arg2
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            long arg2
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            JCTree.JCExpression arg2
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), arg2));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCVariableDecl owner,
            String methodName,
            JCTree.JCExpression arg0,
            JCTree.JCExpression arg1
    ) {
        return method(null, field(owner, methodName), List.of(arg0, arg1));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            JCTree.JCExpression arg0,
            JCTree.JCVariableDecl arg1
    ) {
        return method(null, field(owner, methodName), List.of(arg0, ident(arg1)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCExpression owner,
            String methodName,
            JCTree.JCExpression arg0,
            JCTree.JCExpression arg1,
            JCTree.JCExpression arg2
    ) {
        return method(null, field(owner, methodName), List.of(arg0, arg1, arg2));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            JCTree.JCExpression arg0,
            JCTree.JCExpression arg1,
            JCTree.JCExpression arg2
    ) {
        return method(null, field(owner, methodName), List.of(arg0, arg1, arg2));
    }

    static JCTree.JCMethodInvocation method(
            Name owner,
            String methodName,
            JCTree.JCExpression arg0,
            JCTree.JCExpression arg1,
            JCTree.JCExpression arg2
    ) {
        return method(null, field(ident(owner), methodName), List.of(arg0, arg1, arg2));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            long arg2,
            long arg3
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2), literal(arg3)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            long arg2,
            int arg3
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2), literal(arg3)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            long arg2,
            byte arg3
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2), literal(arg3)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            int arg2,
            byte arg3
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2), literal(arg3)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            long arg2,
            int arg3,
            byte arg4
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2), literal(arg3), literal(arg4)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            long arg2,
            long arg3,
            byte arg4
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2), literal(arg3), literal(arg4)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            long arg2,
            long arg3,
            int arg4
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2), literal(arg3), literal(arg4)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            long arg2,
            long arg3,
            long arg4
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2), literal(arg3), literal(arg4)));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCIdent owner,
            String methodName,
            long arg0,
            long arg1,
            long arg2,
            long arg3,
            int arg4,
            byte arg5
    ) {
        return method(null, field(owner, methodName), List.of(literal(arg0), literal(arg1), literal(arg2), literal(arg3), literal(arg4), literal(arg5)));
    }

    static JCTree.JCMethodInvocation method(
            Name owner,
            String methodName,
            JCTree.JCExpression arg0,
            JCTree.JCExpression arg1,
            JCTree.JCExpression arg2,
            JCTree.JCExpression... args
    ) {
        return method(null, field(ident(owner), methodName), List.of(arg0, arg1, arg2, args));
    }

    static JCTree.JCMethodInvocation method(
            JCTree.JCExpression owner,
            String methodName,
            JCTree.JCExpression arg0,
            JCTree.JCExpression arg1,
            JCTree.JCExpression arg2,
            JCTree.JCExpression... args
    ) {
        return method(null, field(owner, methodName), List.of(arg0, arg1, arg2, args));
    }

    static JCTree.JCMethodInvocation method(List typeArgs, JCTree.JCExpression method, List args) {
        if (typeArgs == null) {
            typeArgs = List.nil();
        }
        if (args == null) {
            args = List.nil();
        }
        return treeMaker.Apply(typeArgs, method, args);
    }

    static JCTree.JCFieldAccess field(JCTree.JCVariableDecl expr, String name) {
        return treeMaker.Select(ident(expr), name(name));
    }

    static JCTree.JCFieldAccess field(JCTree.JCExpression expr, String name) {
        return treeMaker.Select(expr, name(name));
    }

    static JCTree.JCFieldAccess field(Name expr, String name) {
        return treeMaker.Select(ident(expr), name(name));
    }

    static JCTree.JCFieldAccess field(JCTree.JCExpression expr, Name name) {
        return treeMaker.Select(expr, name);
    }

    static JCTree.JCModifiers modifiers(long flag) {
        return treeMaker.Modifiers(flag);
    }

    static JCTree.JCExpressionStatement exec(JCTree.JCExpression expr) {
        return treeMaker.Exec(expr);
    }

    static JCTree.JCAssign assign(JCTree.JCVariableDecl expr1, JCTree.JCExpression expr2) {
        return treeMaker.Assign(ident(expr1), expr2);
    }

    static JCTree.JCAssign assign(Name expr1, JCTree.JCExpression expr2) {
        return treeMaker.Assign(ident(expr1), expr2);
    }

    static JCTree.JCAssign assign(JCTree.JCExpression expr1, JCTree.JCExpression expr2) {
        return treeMaker.Assign(expr1, expr2);
    }

    static JCTree.JCIf defIf(JCTree.JCVariableDecl cond, JCTree.JCStatement thenStmt, JCTree.JCStatement elseStmt) {
        return defIf(ident(cond), thenStmt, elseStmt);
    }

    static JCTree.JCIf defIf(JCTree.JCExpression cond, JCTree.JCStatement thenStmt, JCTree.JCStatement elseStmt) {
        return treeMaker.If(cond, thenStmt, elseStmt);
    }

    static JCTree.JCIf defIf(JCTree.JCExpression cond, JCTree.JCStatement thenStmt) {
        return treeMaker.If(cond, thenStmt, null);
    }

    static JCTree.JCIf defIfReturn(JCTree.JCExpression cond, JCTree.JCStatement thenStmt) {
        return treeMaker.If(cond, block(thenStmt, defReturn()), null);
    }

    static JCTree.JCBinary binary(JCTree.Tag tag, JCTree.JCExpression expr1, JCTree.JCExpression expr2) {
        return treeMaker.Binary(tag, expr1, expr2);
    }

    static JCTree.JCBinary or(JCTree.JCExpression expr1, JCTree.JCExpression expr2) {
        return treeMaker.Binary(JCTree.Tag.OR, expr1, expr2);
    }

    static JCTree.JCBinary lt(JCTree.JCExpression expr1, JCTree.JCExpression expr2) {
        return treeMaker.Binary(JCTree.Tag.LT, expr1, expr2);
    }

    static JCTree.JCBinary lt(JCTree.JCExpression expr1, int expr2) {
        return treeMaker.Binary(JCTree.Tag.LT, expr1, literal(expr2));
    }

    static JCTree.JCBinary lt(JCTree.JCVariableDecl expr1, int expr2) {
        return treeMaker.Binary(JCTree.Tag.LT, ident(expr1), literal(expr2));
    }

    static JCTree.JCBinary eq(JCTree.JCVariableDecl expr1, JCTree.JCExpression expr2) {
        return treeMaker.Binary(JCTree.Tag.EQ, ident(expr1), expr2);
    }

    static JCTree.JCBinary eq(JCTree.JCExpression expr1, JCTree.JCExpression expr2) {
        return treeMaker.Binary(JCTree.Tag.EQ, expr1, expr2);
    }

    static JCTree.JCBinary eq(JCTree.JCExpression expr1, JCTree.JCVariableDecl expr2) {
        return treeMaker.Binary(JCTree.Tag.EQ, expr1, ident(expr2));
    }

    static JCTree.JCBinary eq(JCTree.JCExpression expr1, int expr2) {
        return treeMaker.Binary(JCTree.Tag.EQ, expr1, literal(expr2));
    }

    static JCTree.JCBinary eq(JCTree.JCExpression expr1, long expr2) {
        return treeMaker.Binary(JCTree.Tag.EQ, expr1, literal(expr2));
    }

    static JCTree.JCBinary eq(JCTree.JCVariableDecl expr1, int expr2) {
        return treeMaker.Binary(JCTree.Tag.EQ, ident(expr1), literal(expr2));
    }

    static JCTree.JCBinary notNull(JCTree.JCVariableDecl expr1) {
        return ne(expr1, defNull());
    }

    static JCTree.JCBinary notNull(JCTree.JCExpression expr1) {
        return ne(expr1, defNull());
    }

    static JCTree.JCBinary ne(JCTree.JCExpression expr1, JCTree.JCExpression expr2) {
        return treeMaker.Binary(JCTree.Tag.NE, expr1, expr2);
    }

    static JCTree.JCBinary ne(JCTree.JCVariableDecl expr1, JCTree.JCExpression expr2) {
        return treeMaker.Binary(JCTree.Tag.NE, ident(expr1), expr2);
    }

    static JCTree.JCBinary ne(JCTree.JCVariableDecl expr1, int expr2) {
        return treeMaker.Binary(JCTree.Tag.NE, ident(expr1), literal(expr2));
    }

    static JCTree.JCBinary ne(JCTree.JCVariableDecl expr1, long expr2) {
        return treeMaker.Binary(JCTree.Tag.NE, ident(expr1), literal(expr2));
    }

    static JCTree.JCBinary ne(Name expr1, JCTree.JCExpression expr2) {
        return treeMaker.Binary(JCTree.Tag.NE, ident(expr1), expr2);
    }

    static JCTree.JCBinary ne(JCTree.JCExpression expr1, int value) {
        return treeMaker.Binary(JCTree.Tag.NE, expr1, literal(value));
    }

    static JCTree.JCBinary ne(JCTree.JCExpression expr1, long value) {
        return treeMaker.Binary(JCTree.Tag.NE, expr1, literal(value));
    }

    static JCTree.JCBinary and(JCTree.JCExpression expr1, JCTree.JCExpression expr2) {
        return treeMaker.Binary(JCTree.Tag.AND, expr1, expr2);
    }

    static JCTree.JCBinary bitXor(JCTree.JCExpression expr1, JCTree.JCExpression expr2) {
        return treeMaker.Binary(JCTree.Tag.BITXOR, expr1, expr2);
    }

    static JCTree.JCBinary bitAnd(JCTree.JCExpression expr1, JCTree.JCExpression expr2) {
        return treeMaker.Binary(JCTree.Tag.BITAND, expr1, expr2);
    }

    static JCTree.JCBinary bitAnd(JCTree.JCExpression expr1, long value) {
        return treeMaker.Binary(JCTree.Tag.BITAND, expr1, literal(value));
    }

    static JCTree.JCBinary bitAnd(JCTree.JCVariableDecl expr1, long value) {
        return treeMaker.Binary(JCTree.Tag.BITAND, ident(expr1), literal(value));
    }

    static JCTree.JCBinary bitAnd(JCTree.JCExpression expr1, JSONWriter.Feature value) {
        return treeMaker.Binary(JCTree.Tag.BITAND, expr1, literal(value.mask));
    }

    static JCTree.JCBinary bitOr(JCTree.JCExpression expr1, JCTree.JCExpression expr2) {
        return treeMaker.Binary(JCTree.Tag.BITOR, expr1, expr2);
    }

    static JCTree.JCUnary unary(JCTree.Tag tag, JCTree.JCExpression expr) {
        return treeMaker.Unary(tag, expr);
    }

    static JCTree.JCUnary not(JCTree.JCExpression expr) {
        return treeMaker.Unary(JCTree.Tag.NOT, expr);
    }

    static JCTree.JCUnary not(JCTree.JCVariableDecl var) {
        return treeMaker.Unary(JCTree.Tag.NOT, ident(var));
    }

    static JCTree.JCUnary not(JCTree.JCExpression expr, String name) {
        return not(field(expr, name));
    }

    static JCTree.JCBlock block(JCTree.JCStatement stmt) {
        return block(0L, stmt);
    }

    static JCTree.JCBlock block(JCTree.JCMethodInvocation expr) {
        return block(0L, exec(expr));
    }

    static JCTree.JCBlock block(JCTree.JCStatement... stmts) {
        return block(0L, List.from(stmts));
    }

    static JCTree.JCBlock block(List stmts) {
        return block(0L, stmts);
    }

    static JCTree.JCBlock block(long pos, JCTree.JCStatement stmt) {
        return block(pos, List.of(stmt));
    }

    static JCTree.JCBlock block(long pos, List stmts) {
        return treeMaker.Block(pos, stmts);
    }

    static JCTree.JCLiteral literal(TypeTag tag, Object object) {
        return treeMaker.Literal(tag, object);
    }

    static JCTree.JCExpression literal(byte value) {
        return cast(type(TypeTag.BYTE), treeMaker.Literal(TypeTag.INT, value));
    }

    static JCTree.JCLiteral literal(int value) {
        return treeMaker.Literal(TypeTag.INT, value);
    }

    static JCTree.JCLiteral literal(long value) {
        return treeMaker.Literal(TypeTag.LONG, value);
    }

    static JCTree.JCLiteral literal(Object object) {
        return treeMaker.Literal(object);
    }

    static JCTree.JCTypeCast cast(JCTree type, JCTree.JCExpression expr) {
        return treeMaker.TypeCast(type, expr);
    }

    static JCTree.JCTypeCast cast(TypeTag typeTage, JCTree.JCExpression expr) {
        return treeMaker.TypeCast(type(typeTage), expr);
    }

    static JCTree.JCNewClass newClass(JCTree.JCExpression encl, List typeArgs, JCTree.JCExpression clazz, List args, JCTree.JCClassDecl def) {
        if (typeArgs == null) {
            typeArgs = List.nil();
        }
        if (args == null) {
            args = List.nil();
        }
        return treeMaker.NewClass(encl, typeArgs, clazz, args, def);
    }

    static JCTree.JCPrimitiveTypeTree type(TypeTag tag) {
        return treeMaker.TypeIdent(tag);
    }

    static JCTree.JCLabeledStatement label(String name) {
        return label(name, null);
    }

    static JCTree.JCLabeledStatement label(String name, JCTree.JCStatement stmt) {
        return treeMaker.Labelled(name(name), stmt);
    }

    static JCTree.JCBreak defBreak(JCTree.JCLabeledStatement labeledStatement) {
        Class clazz = treeMaker.getClass();
        try {
            Method method = clazz.getDeclaredMethod("Break", Name.class);
            return (JCTree.JCBreak) method.invoke(treeMaker, labeledStatement.label);
        } catch (Exception e) {
            try {
                Method method = clazz.getDeclaredMethod("Break", JCTree.JCExpression.class);
                return (JCTree.JCBreak) method.invoke(treeMaker, new Object[]{null});
            } catch (Exception ex) {
                throw new RuntimeException(ex);
            }
        }
    }

    static JCTree.JCContinue defContinue(JCTree.JCLabeledStatement labeledStatement) {
        return defContinue(labeledStatement.label);
    }

    static JCTree.JCContinue defContinue(Name name) {
        return treeMaker.Continue(name);
    }

    static JCTree.JCForLoop forLoop(List initStmts, JCTree.JCExpression condExpr, List stepExprs, JCTree.JCStatement bodyStmt) {
        if (initStmts == null) {
            initStmts = List.nil();
        }
        if (stepExprs == null) {
            stepExprs = List.nil();
        }
        return treeMaker.ForLoop(initStmts, condExpr, stepExprs, bodyStmt);
    }

    static JCTree.JCCase defCase(JCTree.JCExpression matchExpr, List matchStmts) {
        if (matchStmts == null) {
            matchStmts = List.nil();
        }
        Class clazz = treeMaker.getClass();
        try {
            Method method = clazz.getDeclaredMethod("Case", JCTree.JCExpression.class, List.class);
            return (JCTree.JCCase) method.invoke(treeMaker, matchExpr, matchStmts);
        } catch (Exception e) {
            try {
                Class caseKind = Class.forName("com.sun.source.tree.CaseTree$CaseKind");
                Field statement = Class.forName("com.sun.tools.javac.tree.JCTree$JCCase").getDeclaredField("STATEMENT");
                Method method = clazz.getDeclaredMethod("Case", caseKind, List.class, List.class, JCTree.class);
                if (JVM_VERSION >= 19 && (matchExpr instanceof JCTree.JCLiteral || matchExpr instanceof JCTree.JCTypeCast)) {
                    Class constantCaseLabel = Class.forName("com.sun.tools.javac.tree.JCTree$JCConstantCaseLabel");
                    Constructor constructor = constantCaseLabel.getDeclaredConstructor(JCTree.JCExpression.class);
                    constructor.setAccessible(true);
                    return (JCTree.JCCase) method.invoke(treeMaker, statement.get(null), List.of(constructor.newInstance(matchExpr)), List.of(block(matchStmts)), null);
                } else {
                    return (JCTree.JCCase) method.invoke(treeMaker, statement.get(null), List.of(matchExpr), List.of(block(matchStmts)), null);
                }
            } catch (Exception e2) {
                try {
                    Class caseKind = Class.forName("com.sun.source.tree.CaseTree$CaseKind");
                    Field statement = Class.forName("com.sun.tools.javac.tree.JCTree$JCCase").getDeclaredField("STATEMENT");
                    Method method = clazz.getDeclaredMethod("Case", caseKind, List.class, JCTree.JCExpression.class, List.class, JCTree.class);
                    if (matchExpr instanceof JCTree.JCLiteral || matchExpr instanceof JCTree.JCTypeCast) {
                        Class constantCaseLabel = Class.forName("com.sun.tools.javac.tree.JCTree$JCConstantCaseLabel");
                        Constructor constructor = constantCaseLabel.getDeclaredConstructor(JCTree.JCExpression.class);
                        constructor.setAccessible(true);
                        return (JCTree.JCCase) method.invoke(treeMaker, statement.get(null), List.of(constructor.newInstance(matchExpr)), null, List.of(block(matchStmts)), null);
                    } else {
                        return (JCTree.JCCase) method.invoke(treeMaker, statement.get(null), List.of(matchExpr), null, List.of(block(matchStmts)), null);
                    }
                } catch (Exception e3) {
                    throw new RuntimeException(e3);
                }
            }
        }
    }

    static JCTree.JCSwitch defSwitch(JCTree.JCExpression selectorExpr, List cases) {
        if (cases == null) {
            cases = List.nil();
        }
        return treeMaker.Switch(selectorExpr, cases);
    }

    static JCTree.JCReturn defReturn(JCTree.JCExpression expr) {
        return treeMaker.Return(expr);
    }

    static JCTree.JCReturn defReturn() {
        return treeMaker.Return(null);
    }

    static JCTree.JCParens parens(JCTree.JCExpression expr) {
        return treeMaker.Parens(expr);
    }

    static JCTree.JCWhileLoop whileLoop(JCTree.JCExpression condExpr, JCTree.JCStatement bodyStmt) {
        return treeMaker.WhileLoop(condExpr, bodyStmt);
    }

    static JCTree.JCTypeApply typeApply(JCTree.JCExpression clazz, List args) {
        if (args == null) {
            args = List.nil();
        }
        return treeMaker.TypeApply(clazz, args);
    }

    static JCTree.JCArrayAccess indexed(JCTree.JCExpression indexedExpr, JCTree.JCExpression indexExpr) {
        return treeMaker.Indexed(indexedExpr, indexExpr);
    }

    static JCTree.JCLambda lambda(JCTree.JCVariableDecl arg, JCTree body) {
        return treeMaker.Lambda(List.of(arg), body);
    }

    static JCTree.JCLambda lambda(List args, JCTree body) {
        if (args == null) {
            args = List.nil();
        }
        return treeMaker.Lambda(args, body);
    }

    static JCTree.JCMemberReference constructorRef(JCTree.JCExpression beanClass) {
        return treeMaker.Reference(MemberReferenceTree.ReferenceMode.NEW, names.init, beanClass, null);
    }

    static JCTree.JCMemberReference methodRef(JCTree.JCExpression beanClass, String methodName) {
        return treeMaker.Reference(MemberReferenceTree.ReferenceMode.INVOKE, names.fromString(methodName), beanClass, null);
    }

    static JCTree.JCNewArray newArray(JCTree.JCExpression elemTypeExpr, List dimsExprs, List elemDataExprs) {
        if (dimsExprs == null) {
            dimsExprs = List.nil();
        }
        return treeMaker.NewArray(elemTypeExpr, dimsExprs, elemDataExprs);
    }

    static JCTree.JCClassDecl defClass(long flag, String name, List typeArgs, JCTree.JCExpression extendExpr, List implementExprs, List defs) {
        if (typeArgs == null) {
            typeArgs = List.nil();
        }
        if (implementExprs == null) {
            implementExprs = List.nil();
        }
        if (defs == null) {
            defs = List.nil();
        }
        return treeMaker.ClassDef(modifiers(flag), name(name), typeArgs, extendExpr, implementExprs, defs);
    }

    static JCTree.JCAnnotation annotation(JCTree type, List args) {
        if (args == null) {
            args = List.nil();
        }
        return treeMaker.Annotation(type, args);
    }

    static JCTree.JCConditional ternary(JCTree.JCExpression cond, JCTree.JCExpression trueExpr, JCTree.JCExpression falseExpr) {
        return treeMaker.Conditional(cond, trueExpr, falseExpr);
    }

    static JCTree.JCConditional ternary(JCTree.JCVariableDecl cond, JCTree.JCExpression trueExpr, JCTree.JCExpression falseExpr) {
        return treeMaker.Conditional(ident(cond), trueExpr, falseExpr);
    }

    static JCTree.JCConditional ternary(JCTree.JCExpression cond, JCTree.JCExpression trueExpr, boolean falseExpr) {
        return treeMaker.Conditional(cond, trueExpr, literal(falseExpr));
    }

    static JCTree.JCConditional ternary(JCTree.JCExpression cond, int trueExpr, int falseExpr) {
        return treeMaker.Conditional(cond, literal(trueExpr), literal(falseExpr));
    }

    static JCTree.JCConditional ternary(JCTree.JCVariableDecl cond, int trueExpr, int falseExpr) {
        return treeMaker.Conditional(ident(cond), literal(trueExpr), literal(falseExpr));
    }

    static JCTree.JCConditional ternary(JCTree.JCExpression cond, long trueExpr, long falseExpr) {
        return treeMaker.Conditional(cond, literal(trueExpr), literal(falseExpr));
    }

    static void pos(int pos) {
        treeMaker.pos = pos;
    }

    static JCTree.JCBinary isDisable(JCTree.JCExpression featureValues, JSONWriter.Feature feature) {
        return eq(bitAnd(featureValues, literal(feature.mask)), 0);
    }

    static JCTree.JCBinary isDisable(JCTree.JCExpression featureValues, JSONWriter.Feature feature0, JSONWriter.Feature feature1) {
        return eq(bitAnd(featureValues, literal(feature0.mask | feature1.mask)), 0);
    }

    static JCTree.JCBinary isEnable(JCTree.JCExpression featureValues, JSONWriter.Feature feature) {
        return ne(bitAnd(featureValues, literal(feature.mask)), 0);
    }

    static JCTree.JCBinary isEnable(JCTree.JCExpression featureValues, JSONWriter.Feature feature0, JSONWriter.Feature feature1) {
        return ne(bitAnd(featureValues, literal(feature0.mask | feature1.mask)), 0);
    }
    static JCTree.JCBinary isEnable(
            JCTree.JCExpression featureValues,
            JSONWriter.Feature feature0,
            JSONWriter.Feature feature1,
            JSONWriter.Feature feature2
    ) {
        return ne(bitAnd(featureValues, feature0.mask | feature1.mask | feature2.mask), 0);
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy