Search in sources :

Example 36 with DynamicClassLoader

use of io.airlift.bytecode.DynamicClassLoader in project trino by trinodb.

the class Bootstrap method bootstrap.

public static CallSite bootstrap(MethodHandles.Lookup callerLookup, String name, MethodType type, long bindingId) {
    ClassLoader classLoader = callerLookup.lookupClass().getClassLoader();
    checkArgument(classLoader instanceof DynamicClassLoader, "Expected %s's classloader to be of type %s", callerLookup.lookupClass().getName(), DynamicClassLoader.class.getName());
    DynamicClassLoader dynamicClassLoader = (DynamicClassLoader) classLoader;
    MethodHandle target = dynamicClassLoader.getCallSiteBindings().get(bindingId);
    checkArgument(target != null, "Binding %s for function %s%s not found", bindingId, name, type.parameterList());
    return new ConstantCallSite(target);
}
Also used : DynamicClassLoader(io.airlift.bytecode.DynamicClassLoader) DynamicClassLoader(io.airlift.bytecode.DynamicClassLoader) ConstantCallSite(java.lang.invoke.ConstantCallSite) MethodHandle(java.lang.invoke.MethodHandle)

Example 37 with DynamicClassLoader

use of io.airlift.bytecode.DynamicClassLoader in project trino by trinodb.

the class StateCompiler method generateStateFactory.

public static <T extends AccumulatorState> AccumulatorStateFactory<T> generateStateFactory(Class<T> clazz, Map<String, Type> fieldTypes) {
    AccumulatorStateMetadata metadata = getMetadataAnnotation(clazz);
    if (metadata != null && metadata.stateFactoryClass() != AccumulatorStateFactory.class) {
        try {
            // noinspection unchecked
            return (AccumulatorStateFactory<T>) metadata.stateFactoryClass().getConstructor().newInstance();
        } catch (InstantiationException | IllegalAccessException | NoSuchMethodException | InvocationTargetException e) {
            throw new RuntimeException(e);
        }
    }
    // grouped aggregation state fields use engine classes, so generated class must be able to see both plugin and system classes
    DynamicClassLoader classLoader = new DynamicClassLoader(clazz.getClassLoader(), StateCompiler.class.getClassLoader());
    Class<? extends T> singleStateClass = generateSingleStateClass(clazz, fieldTypes, classLoader);
    Class<? extends T> groupedStateClass = generateGroupedStateClass(clazz, fieldTypes, classLoader);
    ClassDefinition definition = new ClassDefinition(a(PUBLIC, FINAL), makeClassName(clazz.getSimpleName() + "Factory"), type(Object.class), type(AccumulatorStateFactory.class));
    // Generate constructor
    definition.declareDefaultConstructor(a(PUBLIC));
    // Generate single state creation method
    definition.declareMethod(a(PUBLIC), "createSingleState", type(AccumulatorState.class)).getBody().newObject(singleStateClass).dup().invokeConstructor(singleStateClass).retObject();
    // Generate grouped state creation method
    definition.declareMethod(a(PUBLIC), "createGroupedState", type(AccumulatorState.class)).getBody().newObject(groupedStateClass).dup().invokeConstructor(groupedStateClass).retObject();
    Class<?> factoryClass = defineClass(definition, AccumulatorStateFactory.class, classLoader);
    try {
        // noinspection unchecked
        return (AccumulatorStateFactory<T>) factoryClass.getConstructor().newInstance();
    } catch (ReflectiveOperationException e) {
        throw new RuntimeException(e);
    }
}
Also used : DynamicClassLoader(io.airlift.bytecode.DynamicClassLoader) AccumulatorStateMetadata(io.trino.spi.function.AccumulatorStateMetadata) ClassDefinition(io.airlift.bytecode.ClassDefinition) InvocationTargetException(java.lang.reflect.InvocationTargetException) AccumulatorStateFactory(io.trino.spi.function.AccumulatorStateFactory)

Example 38 with DynamicClassLoader

use of io.airlift.bytecode.DynamicClassLoader in project trino by trinodb.

the class StateCompiler method generateStateSerializer.

public static <T extends AccumulatorState> AccumulatorStateSerializer<T> generateStateSerializer(Class<T> clazz, Map<String, Type> fieldTypes) {
    AccumulatorStateMetadata metadata = getMetadataAnnotation(clazz);
    if (metadata != null && metadata.stateSerializerClass() != AccumulatorStateSerializer.class) {
        try {
            // noinspection unchecked
            return (AccumulatorStateSerializer<T>) metadata.stateSerializerClass().getConstructor().newInstance();
        } catch (InstantiationException | IllegalAccessException | NoSuchMethodException | InvocationTargetException e) {
            throw new RuntimeException(e);
        }
    }
    ClassDefinition definition = new ClassDefinition(a(PUBLIC, FINAL), makeClassName(clazz.getSimpleName() + "Serializer"), type(Object.class), type(AccumulatorStateSerializer.class));
    CallSiteBinder callSiteBinder = new CallSiteBinder();
    // Generate constructor
    definition.declareDefaultConstructor(a(PUBLIC));
    List<StateField> fields = enumerateFields(clazz, fieldTypes);
    generateGetSerializedType(definition, fields, callSiteBinder);
    generateSerialize(definition, callSiteBinder, clazz, fields);
    generateDeserialize(definition, callSiteBinder, clazz, fields);
    // grouped aggregation state fields use engine classes, so generated class must be able to see both plugin and system classes
    DynamicClassLoader classLoader = new DynamicClassLoader(clazz.getClassLoader(), StateCompiler.class.getClassLoader());
    Class<?> serializerClass = defineClass(definition, AccumulatorStateSerializer.class, callSiteBinder.getBindings(), classLoader);
    try {
        // noinspection unchecked
        return (AccumulatorStateSerializer<T>) serializerClass.getConstructor().newInstance();
    } catch (ReflectiveOperationException e) {
        throw new RuntimeException(e);
    }
}
Also used : DynamicClassLoader(io.airlift.bytecode.DynamicClassLoader) AccumulatorStateMetadata(io.trino.spi.function.AccumulatorStateMetadata) AccumulatorStateSerializer(io.trino.spi.function.AccumulatorStateSerializer) ClassDefinition(io.airlift.bytecode.ClassDefinition) InvocationTargetException(java.lang.reflect.InvocationTargetException) CallSiteBinder(io.trino.sql.gen.CallSiteBinder)

Aggregations

DynamicClassLoader (io.airlift.bytecode.DynamicClassLoader)38 Type (io.prestosql.spi.type.Type)20 AccumulatorStateDescriptor (io.prestosql.operator.aggregation.AggregationMetadata.AccumulatorStateDescriptor)19 MethodHandle (java.lang.invoke.MethodHandle)14 ClassDefinition (io.airlift.bytecode.ClassDefinition)11 ImmutableList (com.google.common.collect.ImmutableList)7 BytecodeBlock (io.airlift.bytecode.BytecodeBlock)7 MethodDefinition (io.airlift.bytecode.MethodDefinition)7 Parameter (io.airlift.bytecode.Parameter)7 Variable (io.airlift.bytecode.Variable)7 ArrayType (io.prestosql.spi.type.ArrayType)7 ImmutableList.toImmutableList (com.google.common.collect.ImmutableList.toImmutableList)5 Scope (io.airlift.bytecode.Scope)5 AggregationMetadata (io.prestosql.operator.aggregation.AggregationMetadata)5 ParameterMetadata (io.prestosql.operator.aggregation.AggregationMetadata.ParameterMetadata)5 GenericAccumulatorFactoryBinder (io.prestosql.operator.aggregation.GenericAccumulatorFactoryBinder)5 InternalAggregationFunction (io.prestosql.operator.aggregation.InternalAggregationFunction)5 IfStatement (io.airlift.bytecode.control.IfStatement)4 BytecodeExpression (io.airlift.bytecode.expression.BytecodeExpression)4 CallSiteBinder (io.trino.sql.gen.CallSiteBinder)4