getConvertAction/setConvertAction

Is there anywhere in the codebase that actually uses the ConvertAction to determine how conversion functions are lowered?

In SDValue SelectionDAGLegalize::LegalizeOp(SDValue Op)

case ISD::SINT_TO_FP:

case ISD::UINT_TO_FP:

case ISD::EXTRACT_VECTOR_ELT:

Action = TLI.getOperationAction(Node->getOpcode(),

Node->getOperand(0).getValueType());

This seems incorrect as SINT_TO_FP should be querying the convert action, and not the Operation action.

i.e. it should be:

case ISD::SINT_TO_FP:

case ISD::UINT_TO_FP:

case ISD::FP_TO_SINT:

case ISD::FP_TO_UINT:

Action = TLI.getConvertAction(Node->getValueType(),

Node->getOperand(0).getValueType());

break;

case ISD::EXTRACT_VECTOR_ELT:

Action = TLI.getOperationAction(Node->getOpcode(),

Node->getOperand(0).getValueType());

Is this assumption correct? I cannot get LLVM to expand fp64 → i64 nodes into either to a custom lowered function or expanded to a software function call.

Is getConvertAction being removed? If so, how should I handle this in the backend?

Thanks,

Micah

Is there anywhere in the codebase that actually uses the ConvertAction to determine how conversion functions are lowered?

I don't see any.

In SDValue SelectionDAGLegalize::LegalizeOp(SDValue Op)

...
  case ISD::SINT_TO_FP:
  case ISD::UINT_TO_FP:
  case ISD::EXTRACT_VECTOR_ELT:
    Action = TLI.getOperationAction(Node->getOpcode(),
                                    Node->getOperand(0).getValueType());

This seems incorrect as SINT_TO_FP should be querying the convert action, and not the Operation action.

i.e. it should be:
  case ISD::SINT_TO_FP:
  case ISD::UINT_TO_FP:
  case ISD::FP_TO_SINT:
  case ISD::FP_TO_UINT:
    Action = TLI.getConvertAction(Node->getValueType(),
                                    Node->getOperand(0).getValueType());
      break;
  case ISD::EXTRACT_VECTOR_ELT:
    Action = TLI.getOperationAction(Node->getOpcode(),
                                    Node->getOperand(0).getValueType());

Is this assumption correct? I cannot get LLVM to expand fp64 -> i64 nodes into either to a custom lowered function or expanded to a software function call.

Is getConvertAction being removed? If so, how should I handle this in the backend?

With the current code, FP_TO_SINT and FP_TO_UINT go to the default case,
which looks up getOperationAction with the result type of the cast. So
you need to mark FP_TO_SINT and/or FP_TO_UINT with the result type as
Expand or Custom, if that's flexible enough.

Dan

Dan,
Thanks for the help.

In my specific case, I need to custom lower fp64 <-> i64/i32, but not for any other FP64 conversions. So I need it to be based on the getConvertAction.

I was thinking of modifying it so that if getOperationAction returns 'legal', then we check the actual convert action for what to do. So you make the operation legal, but then expand/promote/custom certain conversions. If getOperationAction returns Custom/Promote/Expand, it trumps getConvertAction.

Like this:

case ISD::SINT_TO_FP:
  case ISD::UINT_TO_FP:
  case ISD::FP_TO_SINT:
  case ISD::FP_TO_UINT:
    // First lets check the operand
    Action = TLI.getOperationAction(Node->getOpcode(),
        Node->getOperand(0).getValueType());
    if (Action == TargetLowering::Legal) {
      // If we are set to legal, then we can specify
      // at a conversion level what to do. What we want to do
      // is specify that the node is legal for
      // and op, but override that for specific versions of the
      // op
      Action = TLI.getConvertAction(Node->getOperand(0).getValueType(),
          Node->getValueType(0));
    }
    break;