Search in sources :

Example 1 with LLVMExpressionNode

use of com.oracle.truffle.llvm.runtime.nodes.api.LLVMExpressionNode in project sulong by graalvm.

the class AsmFactory method createRep.

private void createRep(LLVMExpressionNode body) {
    if ("rep".equals(currentPrefix)) {
        LLVMExpressionNode rcx = getOperandLoad(PrimitiveType.I64, new AsmRegisterOperand("rcx"));
        LLVMAMD64WriteValueNode writeRCX = getStore(PrimitiveType.I64, new AsmRegisterOperand("rcx"));
        LLVMExpressionNode rep = new LLVMAMD64RepNode(writeRCX, rcx, body);
        statements.add(rep);
    } else {
        statements.add(body);
    }
}
Also used : LLVMAMD64WriteValueNode(com.oracle.truffle.llvm.nodes.asm.support.LLVMAMD64WriteValueNode) LLVMAMD64RepNode(com.oracle.truffle.llvm.nodes.asm.LLVMAMD64RepNode) LLVMExpressionNode(com.oracle.truffle.llvm.runtime.nodes.api.LLVMExpressionNode)

Example 2 with LLVMExpressionNode

use of com.oracle.truffle.llvm.runtime.nodes.api.LLVMExpressionNode in project sulong by graalvm.

the class AsmFactory method getOperandStore.

private LLVMExpressionNode getOperandStore(Type type, AsmOperand operand, LLVMExpressionNode from) {
    if (operand instanceof AsmRegisterOperand) {
        AsmRegisterOperand op = (AsmRegisterOperand) operand;
        FrameSlot frame = getRegisterSlot(op.getBaseRegister());
        LLVMExpressionNode register = LLVMAMD64ReadRegisterNodeGen.create(frame);
        int shift = op.getShift();
        LLVMExpressionNode out = null;
        assert (type instanceof PointerType && op.getType() == PrimitiveType.I64) || (op.getType() instanceof PointerType && type == PrimitiveType.I64) || (type == op.getType());
        switch(((PrimitiveType) op.getType()).getPrimitiveKind()) {
            case I8:
                out = LLVMI8ToR64NodeGen.create(shift, register, from);
                break;
            case I16:
                out = LLVMI16ToR64NodeGen.create(register, from);
                break;
            case I32:
                out = LLVMI32ToR64NodeGen.create(from);
                break;
            case I64:
                out = from;
                break;
            default:
                throw new AsmParseException("unsupported operand type: " + op.getType());
        }
        return LLVMWriteI64NodeGen.create(out, frame, null);
    } else if (operand instanceof AsmArgumentOperand) {
        AsmArgumentOperand op = (AsmArgumentOperand) operand;
        Argument info = argInfo.get(op.getIndex());
        if (info.isMemory()) {
            LLVMExpressionNode address = info.getAddress();
            switch(((PrimitiveType) type).getPrimitiveKind()) {
                case I8:
                    return LLVMI8StoreNodeGen.create(address, from);
                case I16:
                    return LLVMI16StoreNodeGen.create(address, from);
                case I32:
                    return LLVMI32StoreNodeGen.create(address, from);
                case I64:
                    return LLVMI64StoreNodeGen.create(address, from);
                default:
                    throw new AsmParseException("unsupported operand type: " + type);
            }
        } else if (info.isRegister()) {
            FrameSlot frame = getRegisterSlot(info.getRegister());
            LLVMExpressionNode register = LLVMAMD64ReadRegisterNodeGen.create(frame);
            LLVMExpressionNode out = null;
            if (type instanceof PointerType || info.getType() instanceof PointerType) {
                return LLVMAMD64WriteAddressRegisterNodeGen.create(sourceLocation, from, frame);
            }
            switch(((PrimitiveType) type).getPrimitiveKind()) {
                case I8:
                    out = LLVMI8ToR64NodeGen.create(0, register, from);
                    break;
                case I16:
                    out = LLVMI16ToR64NodeGen.create(register, from);
                    break;
                case I32:
                    out = LLVMI32ToR64NodeGen.create(from);
                    break;
                case I64:
                    out = from;
                    break;
                default:
                    throw new AsmParseException("unsupported operand type: " + type);
            }
            return LLVMWriteI64NodeGen.create(out, frame, null);
        } else {
            throw new AssertionError("this should not happen; " + info);
        }
    } else if (operand instanceof AsmMemoryOperand) {
        LLVMExpressionNode address = getOperandAddress(operand);
        switch(((PrimitiveType) type).getPrimitiveKind()) {
            case I8:
                return LLVMI8StoreNodeGen.create(null, address, from);
            case I16:
                return LLVMI16StoreNodeGen.create(null, address, from);
            case I32:
                return LLVMI32StoreNodeGen.create(null, address, from);
            case I64:
                return LLVMI64StoreNodeGen.create(null, address, from);
            default:
                throw new AsmParseException("unsupported operand type: " + type);
        }
    }
    throw new AsmParseException("unsupported operand type: " + operand);
}
Also used : FrameSlot(com.oracle.truffle.api.frame.FrameSlot) LLVMExpressionNode(com.oracle.truffle.llvm.runtime.nodes.api.LLVMExpressionNode) PointerType(com.oracle.truffle.llvm.runtime.types.PointerType) PrimitiveType(com.oracle.truffle.llvm.runtime.types.PrimitiveType)

Example 3 with LLVMExpressionNode

use of com.oracle.truffle.llvm.runtime.nodes.api.LLVMExpressionNode in project sulong by graalvm.

the class AsmFactory method getOperandLoad.

private LLVMExpressionNode getOperandLoad(Type typeHint, AsmOperand operand) {
    Type type = typeHint == null ? operand.getType() : typeHint;
    if (operand instanceof AsmRegisterOperand) {
        AsmRegisterOperand op = (AsmRegisterOperand) operand;
        FrameSlot frame = getRegisterSlot(op.getBaseRegister());
        LLVMExpressionNode register = LLVMAMD64ReadRegisterNodeGen.create(frame);
        int shift = op.getShift();
        assert type instanceof PointerType || type == op.getType();
        if (type instanceof PointerType) {
            switch(((PrimitiveType) op.getType()).getPrimitiveKind()) {
                case I8:
                    return LLVMToI8NoZeroExtNodeGen.create(register);
                case I16:
                    return LLVMToI16NoZeroExtNodeGen.create(register);
                case I32:
                    return LLVMToI32NoZeroExtNodeGen.create(register);
                case I64:
                    return LLVMAMD64ReadAddressNodeGen.create(frame);
                default:
                    throw new AsmParseException("unsupported operand type: " + type);
            }
        }
        switch(((PrimitiveType) op.getType()).getPrimitiveKind()) {
            case I8:
                return LLVMAMD64I64ToI8NodeGen.create(shift, register);
            case I16:
                return LLVMToI16NoZeroExtNodeGen.create(register);
            case I32:
                return LLVMToI32NoZeroExtNodeGen.create(register);
            case I64:
                return register;
            default:
                throw new AsmParseException("unsupported operand type: " + type);
        }
    } else if (operand instanceof AsmImmediateOperand) {
        AsmImmediateOperand op = (AsmImmediateOperand) operand;
        if (op.isLabel()) {
            throw new AsmParseException("labels not supported");
        } else {
            switch(((PrimitiveType) type).getPrimitiveKind()) {
                case I8:
                    return LLVMAMD64I8NodeGen.create((byte) op.getValue());
                case I16:
                    return LLVMAMD64I16NodeGen.create((short) op.getValue());
                case I32:
                    return LLVMAMD64I32NodeGen.create((int) op.getValue());
                case I64:
                    return LLVMAMD64I64NodeGen.create(op.getValue());
                default:
                    throw new AsmParseException("unsupported operand type: " + type);
            }
        }
    } else if (operand instanceof AsmArgumentOperand) {
        AsmArgumentOperand op = (AsmArgumentOperand) operand;
        Argument info = argInfo.get(op.getIndex());
        FrameSlot frame = getArgumentSlot(op.getIndex(), type);
        if (info.isMemory()) {
            if (type instanceof PointerType) {
                return LLVMAddressDirectLoadNodeGen.create(LLVMAddressReadNodeGen.create(frame));
            }
            switch(((PrimitiveType) type).getPrimitiveKind()) {
                case I8:
                    return LLVMI8LoadNodeGen.create(LLVMAddressReadNodeGen.create(frame));
                case I16:
                    return LLVMI16LoadNodeGen.create(LLVMAddressReadNodeGen.create(frame));
                case I32:
                    return LLVMI32LoadNodeGen.create(LLVMAddressReadNodeGen.create(frame));
                case I64:
                    return LLVMI64LoadNodeGen.create(LLVMAddressReadNodeGen.create(frame));
                default:
                    throw new AsmParseException("unsupported operand type: " + type);
            }
        } else if (info.isRegister()) {
            frame = getRegisterSlot(info.getRegister());
            if (type instanceof PointerType) {
                return LLVMAMD64ReadAddressNodeGen.create(frame);
            }
            LLVMExpressionNode register = LLVMAMD64ReadRegisterNodeGen.create(frame);
            switch(((PrimitiveType) type).getPrimitiveKind()) {
                case I8:
                    return LLVMToI8NoZeroExtNodeGen.create(register);
                case I16:
                    return LLVMToI16NoZeroExtNodeGen.create(register);
                case I32:
                    return LLVMToI32NoZeroExtNodeGen.create(register);
                case I64:
                    return LLVMToI64NoZeroExtNodeGen.create(register);
                default:
                    throw new AsmParseException("unsupported operand type: " + type);
            }
        } else {
            // constraint "0"-"9"
            if (type instanceof PointerType) {
                return LLVMAMD64ReadAddressNodeGen.create(frame);
            }
            LLVMExpressionNode register = LLVMAMD64ReadRegisterNodeGen.create(frame);
            switch(((PrimitiveType) type).getPrimitiveKind()) {
                case I8:
                    return LLVMToI8NoZeroExtNodeGen.create(register);
                case I16:
                    return LLVMToI16NoZeroExtNodeGen.create(register);
                case I32:
                    return LLVMToI32NoZeroExtNodeGen.create(register);
                case I64:
                    return LLVMToI64NoZeroExtNodeGen.create(register);
                default:
                    throw new AsmParseException("unsupported operand type: " + type);
            }
        }
    } else if (operand instanceof AsmMemoryOperand) {
        LLVMExpressionNode address = getOperandAddress(operand);
        LLVMExpressionNode addr = LLVMToAddressNodeGen.create(address);
        if (type instanceof PrimitiveType) {
            switch(((PrimitiveType) type).getPrimitiveKind()) {
                case I8:
                    return LLVMI8LoadNodeGen.create(addr);
                case I16:
                    return LLVMI16LoadNodeGen.create(addr);
                case I32:
                    return LLVMI32LoadNodeGen.create(addr);
                case I64:
                    return LLVMI64LoadNodeGen.create(addr);
                default:
                    throw new AsmParseException("unsupported operand type: " + type);
            }
        } else if (type instanceof PointerType) {
            return LLVMAddressDirectLoadNodeGen.create(addr);
        } else {
            throw new AsmParseException("unsupported operand type: " + type);
        }
    }
    throw new AsmParseException("unsupported operand: " + operand);
}
Also used : PrimitiveType(com.oracle.truffle.llvm.runtime.types.PrimitiveType) PointerType(com.oracle.truffle.llvm.runtime.types.PointerType) StructureType(com.oracle.truffle.llvm.runtime.types.StructureType) VoidType(com.oracle.truffle.llvm.runtime.types.VoidType) Type(com.oracle.truffle.llvm.runtime.types.Type) FrameSlot(com.oracle.truffle.api.frame.FrameSlot) LLVMExpressionNode(com.oracle.truffle.llvm.runtime.nodes.api.LLVMExpressionNode) PointerType(com.oracle.truffle.llvm.runtime.types.PointerType) PrimitiveType(com.oracle.truffle.llvm.runtime.types.PrimitiveType)

Example 4 with LLVMExpressionNode

use of com.oracle.truffle.llvm.runtime.nodes.api.LLVMExpressionNode in project sulong by graalvm.

the class AsmFactory method createUnaryOperation.

void createUnaryOperation(String operation, AsmOperand operand) {
    LLVMExpressionNode src;
    LLVMExpressionNode out;
    AsmOperand dst = operand;
    Type dstType;
    assert operation.length() > 0;
    char suffix = operation.charAt(operation.length() - 1);
    dstType = getPrimitiveTypeFromSuffix(suffix);
    src = getOperandLoad(dstType, operand);
    switch(operation) {
        case "incb":
            out = LLVMAMD64IncbNodeGen.create(getUpdatePZSOFlagsNode(), src);
            break;
        case "incw":
            out = LLVMAMD64IncwNodeGen.create(getUpdatePZSOFlagsNode(), src);
            break;
        case "incl":
            out = LLVMAMD64InclNodeGen.create(getUpdatePZSOFlagsNode(), src);
            break;
        case "incq":
            out = LLVMAMD64IncqNodeGen.create(getUpdatePZSOFlagsNode(), src);
            break;
        case "decb":
            out = LLVMAMD64DecbNodeGen.create(getUpdatePZSOFlagsNode(), src);
            break;
        case "decw":
            out = LLVMAMD64DecwNodeGen.create(getUpdatePZSOFlagsNode(), src);
            break;
        case "decl":
            out = LLVMAMD64DeclNodeGen.create(getUpdatePZSOFlagsNode(), src);
            break;
        case "decq":
            out = LLVMAMD64DecqNodeGen.create(getUpdatePZSOFlagsNode(), src);
            break;
        case "negb":
            out = LLVMAMD64NegbNodeGen.create(getUpdateCPZSOFlagsNode(), src);
            break;
        case "negw":
            out = LLVMAMD64NegwNodeGen.create(getUpdateCPZSOFlagsNode(), src);
            break;
        case "negl":
            out = LLVMAMD64NeglNodeGen.create(getUpdateCPZSOFlagsNode(), src);
            break;
        case "negq":
            out = LLVMAMD64NegqNodeGen.create(getUpdateCPZSOFlagsNode(), src);
            break;
        case "notb":
            out = LLVMAMD64NotbNodeGen.create(src);
            break;
        case "notw":
            out = LLVMAMD64NotwNodeGen.create(src);
            break;
        case "notl":
            out = LLVMAMD64NotlNodeGen.create(src);
            break;
        case "notq":
            out = LLVMAMD64NotqNodeGen.create(src);
            break;
        case "idivb":
            out = LLVMAMD64IdivbNodeGen.create(getOperandLoad(PrimitiveType.I16, new AsmRegisterOperand("ax")), src);
            dst = new AsmRegisterOperand("ax");
            dstType = PrimitiveType.I16;
            break;
        case "idivw":
            {
                LLVMAMD64WriteTupelNode res = LLVMAMD64WriteTupelNodeGen.create(getRegisterStore("ax"), getRegisterStore("dx"));
                LLVMExpressionNode high = getOperandLoad(PrimitiveType.I16, new AsmRegisterOperand("dx"));
                out = LLVMAMD64IdivwNodeGen.create(res, high, getOperandLoad(PrimitiveType.I16, new AsmRegisterOperand("ax")), src);
                statements.add(out);
                return;
            }
        case "idivl":
            {
                LLVMAMD64WriteTupelNode res = LLVMAMD64WriteTupelNodeGen.create(getRegisterStore("eax"), getRegisterStore("edx"));
                LLVMExpressionNode high = getOperandLoad(PrimitiveType.I32, new AsmRegisterOperand("edx"));
                out = LLVMAMD64IdivlNodeGen.create(res, high, getOperandLoad(PrimitiveType.I32, new AsmRegisterOperand("eax")), src);
                statements.add(out);
                return;
            }
        case "idivq":
            {
                LLVMAMD64WriteTupelNode res = LLVMAMD64WriteTupelNodeGen.create(getRegisterStore("rax"), getRegisterStore("rdx"));
                LLVMExpressionNode high = getOperandLoad(PrimitiveType.I64, new AsmRegisterOperand("rdx"));
                out = LLVMAMD64IdivqNodeGen.create(res, high, getOperandLoad(PrimitiveType.I64, new AsmRegisterOperand("rax")), src);
                statements.add(out);
                return;
            }
        case "imulb":
            out = LLVMAMD64ImulbNodeGen.create(getFlagWrite(LLVMAMD64Flags.CF), getFlagWrite(LLVMAMD64Flags.PF), getFlagWrite(LLVMAMD64Flags.AF), getFlagWrite(LLVMAMD64Flags.ZF), getFlagWrite(LLVMAMD64Flags.SF), getFlagWrite(LLVMAMD64Flags.OF), getOperandLoad(PrimitiveType.I8, new AsmRegisterOperand("al")), src);
            dst = new AsmRegisterOperand("ax");
            dstType = PrimitiveType.I16;
            break;
        case "imulw":
            {
                LLVMAMD64WriteTupelNode res = LLVMAMD64WriteTupelNodeGen.create(getRegisterStore("ax"), getRegisterStore("dx"));
                out = LLVMAMD64ImulwNodeGen.create(getFlagWrite(LLVMAMD64Flags.CF), getFlagWrite(LLVMAMD64Flags.PF), getFlagWrite(LLVMAMD64Flags.AF), getFlagWrite(LLVMAMD64Flags.ZF), getFlagWrite(LLVMAMD64Flags.SF), getFlagWrite(LLVMAMD64Flags.OF), res, getOperandLoad(PrimitiveType.I16, new AsmRegisterOperand("ax")), src);
                statements.add(out);
                return;
            }
        case "imull":
            {
                LLVMAMD64WriteTupelNode res = LLVMAMD64WriteTupelNodeGen.create(getRegisterStore("eax"), getRegisterStore("edx"));
                out = LLVMAMD64ImullNodeGen.create(getFlagWrite(LLVMAMD64Flags.CF), getFlagWrite(LLVMAMD64Flags.PF), getFlagWrite(LLVMAMD64Flags.AF), getFlagWrite(LLVMAMD64Flags.ZF), getFlagWrite(LLVMAMD64Flags.SF), getFlagWrite(LLVMAMD64Flags.OF), res, getOperandLoad(PrimitiveType.I32, new AsmRegisterOperand("eax")), src);
                statements.add(out);
                return;
            }
        case "imulq":
            {
                LLVMAMD64WriteTupelNode res = LLVMAMD64WriteTupelNodeGen.create(getRegisterStore("rax"), getRegisterStore("rdx"));
                out = LLVMAMD64ImulqNodeGen.create(getFlagWrite(LLVMAMD64Flags.CF), getFlagWrite(LLVMAMD64Flags.PF), getFlagWrite(LLVMAMD64Flags.AF), getFlagWrite(LLVMAMD64Flags.ZF), getFlagWrite(LLVMAMD64Flags.SF), getFlagWrite(LLVMAMD64Flags.OF), res, getOperandLoad(PrimitiveType.I64, new AsmRegisterOperand("rax")), src);
                statements.add(out);
                return;
            }
        case "divb":
            out = LLVMAMD64DivbNodeGen.create(getOperandLoad(PrimitiveType.I16, new AsmRegisterOperand("ax")), src);
            dst = new AsmRegisterOperand("ax");
            dstType = PrimitiveType.I16;
            break;
        case "divw":
            {
                LLVMAMD64WriteTupelNode res = LLVMAMD64WriteTupelNodeGen.create(getRegisterStore("ax"), getRegisterStore("dx"));
                LLVMExpressionNode high = getOperandLoad(PrimitiveType.I16, new AsmRegisterOperand("dx"));
                out = LLVMAMD64DivwNodeGen.create(res, high, getOperandLoad(PrimitiveType.I16, new AsmRegisterOperand("ax")), src);
                statements.add(out);
                return;
            }
        case "divl":
            {
                LLVMAMD64WriteTupelNode res = LLVMAMD64WriteTupelNodeGen.create(getRegisterStore("eax"), getRegisterStore("edx"));
                LLVMExpressionNode high = getOperandLoad(PrimitiveType.I32, new AsmRegisterOperand("edx"));
                out = LLVMAMD64DivlNodeGen.create(res, high, getOperandLoad(PrimitiveType.I32, new AsmRegisterOperand("eax")), src);
                statements.add(out);
                return;
            }
        case "divq":
            {
                LLVMAMD64WriteTupelNode res = LLVMAMD64WriteTupelNodeGen.create(getRegisterStore("rax"), getRegisterStore("rdx"));
                LLVMExpressionNode high = getOperandLoad(PrimitiveType.I64, new AsmRegisterOperand("rdx"));
                out = LLVMAMD64DivqNodeGen.create(res, high, getOperandLoad(PrimitiveType.I64, new AsmRegisterOperand("rax")), src);
                statements.add(out);
                return;
            }
        case "mulb":
            out = LLVMAMD64MulbNodeGen.create(getFlagWrite(LLVMAMD64Flags.CF), getFlagWrite(LLVMAMD64Flags.PF), getFlagWrite(LLVMAMD64Flags.AF), getFlagWrite(LLVMAMD64Flags.ZF), getFlagWrite(LLVMAMD64Flags.SF), getFlagWrite(LLVMAMD64Flags.OF), getOperandLoad(PrimitiveType.I8, new AsmRegisterOperand("al")), src);
            dst = new AsmRegisterOperand("ax");
            dstType = PrimitiveType.I16;
            break;
        case "mulw":
            {
                LLVMAMD64WriteTupelNode res = LLVMAMD64WriteTupelNodeGen.create(getRegisterStore("ax"), getRegisterStore("dx"));
                out = LLVMAMD64MulwNodeGen.create(getFlagWrite(LLVMAMD64Flags.CF), getFlagWrite(LLVMAMD64Flags.PF), getFlagWrite(LLVMAMD64Flags.AF), getFlagWrite(LLVMAMD64Flags.ZF), getFlagWrite(LLVMAMD64Flags.SF), getFlagWrite(LLVMAMD64Flags.OF), res, getOperandLoad(PrimitiveType.I16, new AsmRegisterOperand("ax")), src);
                statements.add(out);
                return;
            }
        case "mull":
            {
                LLVMAMD64WriteTupelNode res = LLVMAMD64WriteTupelNodeGen.create(getRegisterStore("eax"), getRegisterStore("edx"));
                out = LLVMAMD64MullNodeGen.create(getFlagWrite(LLVMAMD64Flags.CF), getFlagWrite(LLVMAMD64Flags.PF), getFlagWrite(LLVMAMD64Flags.AF), getFlagWrite(LLVMAMD64Flags.ZF), getFlagWrite(LLVMAMD64Flags.SF), getFlagWrite(LLVMAMD64Flags.OF), res, getOperandLoad(PrimitiveType.I32, new AsmRegisterOperand("eax")), src);
                statements.add(out);
                return;
            }
        case "mulq":
            {
                LLVMAMD64WriteTupelNode res = LLVMAMD64WriteTupelNodeGen.create(getRegisterStore("rax"), getRegisterStore("rdx"));
                out = LLVMAMD64MulqNodeGen.create(getFlagWrite(LLVMAMD64Flags.CF), getFlagWrite(LLVMAMD64Flags.PF), getFlagWrite(LLVMAMD64Flags.AF), getFlagWrite(LLVMAMD64Flags.ZF), getFlagWrite(LLVMAMD64Flags.SF), getFlagWrite(LLVMAMD64Flags.OF), res, getOperandLoad(PrimitiveType.I64, new AsmRegisterOperand("rax")), src);
                statements.add(out);
                return;
            }
        case "bswapl":
            out = LLVMAMD64BswaplNodeGen.create(src);
            break;
        case "bswapq":
            out = LLVMAMD64BswapqNodeGen.create(src);
            break;
        case "popw":
            out = LLVMAMD64PopwNodeGen.create();
            break;
        case "popl":
            out = LLVMAMD64PoplNodeGen.create();
            break;
        case "popq":
            out = LLVMAMD64PopqNodeGen.create();
            break;
        case "pushw":
            statements.add(LLVMAMD64PushwNodeGen.create(src));
            return;
        case "pushl":
            statements.add(LLVMAMD64PushlNodeGen.create(src));
            return;
        case "pushq":
            statements.add(LLVMAMD64PushqNodeGen.create(src));
            return;
        default:
            statements.add(new LLVMUnsupportedInlineAssemblerNode(sourceLocation, "Unsupported operation: " + operation));
            return;
    }
    LLVMExpressionNode write = getOperandStore(dstType, dst, out);
    statements.add(write);
}
Also used : PrimitiveType(com.oracle.truffle.llvm.runtime.types.PrimitiveType) PointerType(com.oracle.truffle.llvm.runtime.types.PointerType) StructureType(com.oracle.truffle.llvm.runtime.types.StructureType) VoidType(com.oracle.truffle.llvm.runtime.types.VoidType) Type(com.oracle.truffle.llvm.runtime.types.Type) LLVMAMD64WriteTupelNode(com.oracle.truffle.llvm.nodes.asm.support.LLVMAMD64WriteTupelNode) LLVMExpressionNode(com.oracle.truffle.llvm.runtime.nodes.api.LLVMExpressionNode) LLVMUnsupportedInlineAssemblerNode(com.oracle.truffle.llvm.nodes.others.LLVMUnsupportedInlineAssemblerNode)

Example 5 with LLVMExpressionNode

use of com.oracle.truffle.llvm.runtime.nodes.api.LLVMExpressionNode in project sulong by graalvm.

the class LLVMSymbolReadResolver method resolveElementPointer.

public LLVMExpressionNode resolveElementPointer(SymbolImpl base, List<SymbolImpl> indices) {
    LLVMExpressionNode currentAddress = resolve(base);
    Type currentType = base.getType();
    for (int i = 0, indicesSize = indices.size(); i < indicesSize; i++) {
        final SymbolImpl indexSymbol = indices.get(i);
        final Type indexType = indexSymbol.getType();
        final Long indexInteger = evaluateLongIntegerConstant(indexSymbol);
        if (indexInteger == null) {
            // the index is determined at runtime
            if (currentType instanceof StructureType) {
                // according to http://llvm.org/docs/LangRef.html#getelementptr-instruction
                throw new IllegalStateException("Indices on structs must be constant integers!");
            }
            AggregateType aggregate = (AggregateType) currentType;
            final long indexedTypeLength = runtime.getContext().getIndexOffset(1, aggregate);
            currentType = aggregate.getElementType(1);
            final LLVMExpressionNode indexNode = resolve(indexSymbol);
            currentAddress = runtime.getNodeFactory().createTypedElementPointer(runtime, currentAddress, indexNode, indexedTypeLength, currentType);
        } else {
            // the index is a constant integer
            AggregateType aggregate = (AggregateType) currentType;
            final long addressOffset = runtime.getContext().getIndexOffset(indexInteger, aggregate);
            currentType = aggregate.getElementType(indexInteger);
            // computed by getelementptr even if it is the same as the basepointer
            if (addressOffset != 0 || i == indicesSize - 1) {
                final LLVMExpressionNode indexNode;
                if (indexType == PrimitiveType.I32) {
                    indexNode = runtime.getNodeFactory().createLiteral(runtime, 1, PrimitiveType.I32);
                } else if (indexType == PrimitiveType.I64) {
                    indexNode = runtime.getNodeFactory().createLiteral(runtime, 1L, PrimitiveType.I64);
                } else {
                    throw new AssertionError(indexType);
                }
                currentAddress = runtime.getNodeFactory().createTypedElementPointer(runtime, currentAddress, indexNode, addressOffset, currentType);
            }
        }
    }
    return currentAddress;
}
Also used : SymbolImpl(com.oracle.truffle.llvm.parser.model.SymbolImpl) VariableBitWidthType(com.oracle.truffle.llvm.runtime.types.VariableBitWidthType) LLVMConversionType(com.oracle.truffle.llvm.parser.instructions.LLVMConversionType) PrimitiveType(com.oracle.truffle.llvm.runtime.types.PrimitiveType) MetaType(com.oracle.truffle.llvm.runtime.types.MetaType) VectorType(com.oracle.truffle.llvm.runtime.types.VectorType) StructureType(com.oracle.truffle.llvm.runtime.types.StructureType) ArrayType(com.oracle.truffle.llvm.runtime.types.ArrayType) AggregateType(com.oracle.truffle.llvm.runtime.types.AggregateType) OpaqueType(com.oracle.truffle.llvm.runtime.types.OpaqueType) LLVMArithmeticInstructionType(com.oracle.truffle.llvm.parser.instructions.LLVMArithmeticInstructionType) Type(com.oracle.truffle.llvm.runtime.types.Type) PointerType(com.oracle.truffle.llvm.runtime.types.PointerType) FunctionType(com.oracle.truffle.llvm.runtime.types.FunctionType) VoidType(com.oracle.truffle.llvm.runtime.types.VoidType) StructureType(com.oracle.truffle.llvm.runtime.types.StructureType) LLVMExpressionNode(com.oracle.truffle.llvm.runtime.nodes.api.LLVMExpressionNode) AggregateType(com.oracle.truffle.llvm.runtime.types.AggregateType)

Aggregations

LLVMExpressionNode (com.oracle.truffle.llvm.runtime.nodes.api.LLVMExpressionNode)53 PointerType (com.oracle.truffle.llvm.runtime.types.PointerType)39 PrimitiveType (com.oracle.truffle.llvm.runtime.types.PrimitiveType)38 StructureType (com.oracle.truffle.llvm.runtime.types.StructureType)35 Type (com.oracle.truffle.llvm.runtime.types.Type)33 FunctionType (com.oracle.truffle.llvm.runtime.types.FunctionType)27 ArrayType (com.oracle.truffle.llvm.runtime.types.ArrayType)26 LLVMArithmeticInstructionType (com.oracle.truffle.llvm.parser.instructions.LLVMArithmeticInstructionType)24 LLVMConversionType (com.oracle.truffle.llvm.parser.instructions.LLVMConversionType)24 AggregateType (com.oracle.truffle.llvm.runtime.types.AggregateType)24 FrameSlot (com.oracle.truffle.api.frame.FrameSlot)12 VoidType (com.oracle.truffle.llvm.runtime.types.VoidType)11 SymbolImpl (com.oracle.truffle.llvm.parser.model.SymbolImpl)8 LLVMSourceLocation (com.oracle.truffle.llvm.runtime.debug.scope.LLVMSourceLocation)7 LLVMControlFlowNode (com.oracle.truffle.llvm.runtime.nodes.api.LLVMControlFlowNode)7 ArrayList (java.util.ArrayList)7 LLVMUnsupportedInlineAssemblerNode (com.oracle.truffle.llvm.nodes.others.LLVMUnsupportedInlineAssemblerNode)5 Phi (com.oracle.truffle.llvm.parser.LLVMPhiManager.Phi)4 AttributesGroup (com.oracle.truffle.llvm.parser.model.attributes.AttributesGroup)4 MetaType (com.oracle.truffle.llvm.runtime.types.MetaType)4