Search in sources :

Example 11 with InvocationArgumentConvention

use of io.trino.spi.function.InvocationConvention.InvocationArgumentConvention in project trino by trinodb.

the class PolymorphicScalarFunction method matchesParameterAndReturnTypes.

private static boolean matchesParameterAndReturnTypes(MethodAndNativeContainerTypes methodAndNativeContainerTypes, BoundSignature boundSignature, List<InvocationArgumentConvention> argumentConventions, InvocationReturnConvention returnConvention) {
    Method method = methodAndNativeContainerTypes.getMethod();
    checkState(method.getParameterCount() >= boundSignature.getArity(), "method %s has not enough arguments: %s (should have at least %s)", method.getName(), method.getParameterCount(), boundSignature.getArity());
    Class<?>[] methodParameterJavaTypes = method.getParameterTypes();
    int methodParameterIndex = 0;
    for (int i = 0; i < boundSignature.getArity(); i++) {
        Type resolvedType = boundSignature.getArgumentType(i);
        InvocationArgumentConvention argumentConvention = argumentConventions.get(i);
        Class<?> expectedType = null;
        Class<?> actualType;
        switch(argumentConvention) {
            case NEVER_NULL:
            case NULL_FLAG:
                expectedType = methodParameterJavaTypes[methodParameterIndex];
                actualType = resolvedType.getJavaType();
                break;
            case BOXED_NULLABLE:
                expectedType = methodParameterJavaTypes[methodParameterIndex];
                actualType = Primitives.wrap(resolvedType.getJavaType());
                break;
            case BLOCK_POSITION:
                Optional<Class<?>> explicitNativeContainerTypes = methodAndNativeContainerTypes.getExplicitNativeContainerTypes().get(i);
                if (explicitNativeContainerTypes.isPresent()) {
                    expectedType = explicitNativeContainerTypes.get();
                }
                actualType = resolvedType.getJavaType();
                break;
            default:
                throw new UnsupportedOperationException("Unknown argument convention: " + argumentConvention);
        }
        if (!actualType.equals(expectedType)) {
            return false;
        }
        methodParameterIndex += argumentConvention.getParameterCount();
    }
    return method.getReturnType().equals(getNullAwareContainerType(boundSignature.getReturnType().getJavaType(), returnConvention));
}
Also used : Type(io.trino.spi.type.Type) InvocationArgumentConvention(io.trino.spi.function.InvocationConvention.InvocationArgumentConvention) Method(java.lang.reflect.Method)

Example 12 with InvocationArgumentConvention

use of io.trino.spi.function.InvocationConvention.InvocationArgumentConvention in project trino by trinodb.

the class PolymorphicScalarFunction method applyExtraParameters.

private MethodHandle applyExtraParameters(Method matchingMethod, List<Object> extraParameters, List<InvocationArgumentConvention> argumentConventions) {
    int expectedArgumentsCount = extraParameters.size() + argumentConventions.stream().mapToInt(InvocationArgumentConvention::getParameterCount).sum();
    int matchingMethodArgumentCount = matchingMethod.getParameterCount();
    checkState(matchingMethodArgumentCount == expectedArgumentsCount, "method %s has invalid number of arguments: %s (should have %s)", matchingMethod.getName(), matchingMethodArgumentCount, expectedArgumentsCount);
    MethodHandle matchingMethodHandle = Reflection.methodHandle(matchingMethod);
    matchingMethodHandle = MethodHandles.insertArguments(matchingMethodHandle, matchingMethodArgumentCount - extraParameters.size(), extraParameters.toArray());
    return matchingMethodHandle;
}
Also used : InvocationArgumentConvention(io.trino.spi.function.InvocationConvention.InvocationArgumentConvention) MethodHandle(java.lang.invoke.MethodHandle)

Example 13 with InvocationArgumentConvention

use of io.trino.spi.function.InvocationConvention.InvocationArgumentConvention in project trino by trinodb.

the class ArrayJoin method specializeArrayJoin.

private static ChoicesScalarFunctionImplementation specializeArrayJoin(BoundSignature boundSignature, FunctionDependencies functionDependencies, MethodHandle methodHandle) {
    List<InvocationArgumentConvention> argumentConventions = Collections.nCopies(boundSignature.getArity(), NEVER_NULL);
    Type type = ((ArrayType) boundSignature.getArgumentTypes().get(0)).getElementType();
    if (type instanceof UnknownType) {
        return new ChoicesScalarFunctionImplementation(boundSignature, FAIL_ON_NULL, argumentConventions, methodHandle.bindTo(null), Optional.of(STATE_FACTORY));
    } else {
        try {
            InvocationConvention convention = new InvocationConvention(ImmutableList.of(BLOCK_POSITION), NULLABLE_RETURN, true, false);
            MethodHandle cast = functionDependencies.getCastInvoker(type, VARCHAR, convention).getMethodHandle();
            // if the cast doesn't take a ConnectorSession, create an adapter that drops the provided session
            if (cast.type().parameterArray()[0] != ConnectorSession.class) {
                cast = MethodHandles.dropArguments(cast, 0, ConnectorSession.class);
            }
            MethodHandle target = MethodHandles.insertArguments(methodHandle, 0, cast);
            return new ChoicesScalarFunctionImplementation(boundSignature, FAIL_ON_NULL, argumentConventions, target, Optional.of(STATE_FACTORY));
        } catch (TrinoException e) {
            throw new TrinoException(INVALID_FUNCTION_ARGUMENT, format("Input type %s not supported", type), e);
        }
    }
}
Also used : ArrayType(io.trino.spi.type.ArrayType) UnknownType(io.trino.type.UnknownType) Type(io.trino.spi.type.Type) TypeSignature.arrayType(io.trino.spi.type.TypeSignature.arrayType) ArrayType(io.trino.spi.type.ArrayType) UnknownType(io.trino.type.UnknownType) InvocationArgumentConvention(io.trino.spi.function.InvocationConvention.InvocationArgumentConvention) InvocationConvention(io.trino.spi.function.InvocationConvention) TrinoException(io.trino.spi.TrinoException) ConnectorSession(io.trino.spi.connector.ConnectorSession) MethodHandle(java.lang.invoke.MethodHandle)

Example 14 with InvocationArgumentConvention

use of io.trino.spi.function.InvocationConvention.InvocationArgumentConvention in project trino by trinodb.

the class TestScalarFunctionAdapter method toCallArgumentValues.

private static List<Object> toCallArgumentValues(InvocationConvention callingConvention, BitSet nullArguments, Target target, List<Type> argumentTypes) {
    List<Object> callArguments = new ArrayList<>();
    callArguments.add(target);
    for (int i = 0; i < callingConvention.getArgumentConventions().size(); i++) {
        Type argumentType = argumentTypes.get(i);
        boolean nullArgument = nullArguments.get(i);
        Object testValue;
        if (nullArgument) {
            testValue = null;
        } else {
            testValue = getTestValue(argumentType);
        }
        InvocationArgumentConvention argumentConvention = callingConvention.getArgumentConvention(i);
        switch(argumentConvention) {
            case NEVER_NULL:
                verify(testValue != null, "null can not be passed to a never null argument");
                callArguments.add(testValue);
                break;
            case BOXED_NULLABLE:
                callArguments.add(testValue);
                break;
            case NULL_FLAG:
                callArguments.add(testValue == null ? Defaults.defaultValue(argumentType.getJavaType()) : testValue);
                callArguments.add(testValue == null);
                break;
            case BLOCK_POSITION:
                BlockBuilder blockBuilder = argumentType.createBlockBuilder(null, 3);
                blockBuilder.appendNull();
                writeNativeValue(argumentType, blockBuilder, testValue);
                blockBuilder.appendNull();
                callArguments.add(blockBuilder.build());
                callArguments.add(1);
                break;
            default:
                throw new IllegalArgumentException("Unsupported argument convention: " + argumentConvention);
        }
    }
    return callArguments;
}
Also used : CharType.createCharType(io.trino.spi.type.CharType.createCharType) TimestampType.createTimestampType(io.trino.spi.type.TimestampType.createTimestampType) ArrayType(io.trino.spi.type.ArrayType) Type(io.trino.spi.type.Type) TimestampType(io.trino.spi.type.TimestampType) MethodType.methodType(java.lang.invoke.MethodType.methodType) MethodType(java.lang.invoke.MethodType) CharType(io.trino.spi.type.CharType) InvocationArgumentConvention(io.trino.spi.function.InvocationConvention.InvocationArgumentConvention) ArrayList(java.util.ArrayList) BlockBuilder(io.trino.spi.block.BlockBuilder)

Aggregations

InvocationArgumentConvention (io.trino.spi.function.InvocationConvention.InvocationArgumentConvention)14 Type (io.trino.spi.type.Type)8 MethodType (java.lang.invoke.MethodType)7 MethodHandle (java.lang.invoke.MethodHandle)4 MethodType.methodType (java.lang.invoke.MethodType.methodType)4 ArrayList (java.util.ArrayList)4 ConnectorSession (io.trino.spi.connector.ConnectorSession)3 ArrayType (io.trino.spi.type.ArrayType)3 ImmutableList (com.google.common.collect.ImmutableList)2 ImmutableList.toImmutableList (com.google.common.collect.ImmutableList.toImmutableList)2 LongVariableConstraint (io.trino.metadata.LongVariableConstraint)2 TrinoException (io.trino.spi.TrinoException)2 InvocationConvention (io.trino.spi.function.InvocationConvention)2 InvocationReturnConvention (io.trino.spi.function.InvocationConvention.InvocationReturnConvention)2 CharType (io.trino.spi.type.CharType)2 CharType.createCharType (io.trino.spi.type.CharType.createCharType)2 TimestampType (io.trino.spi.type.TimestampType)2 TimestampType.createTimestampType (io.trino.spi.type.TimestampType.createTimestampType)2 List (java.util.List)2 BytecodeBlock (io.airlift.bytecode.BytecodeBlock)1