[CAPI] Expose CastInst::getCastOpcode in C API

Reviewed By: deadalnix

Differential Revision: https://reviews.llvm.org/D91514
This commit is contained in:
Jack Andersen 2022-04-30 18:40:04 -04:00
parent 2e7e0975c0
commit 09325d3606
4 changed files with 75 additions and 0 deletions

View File

@ -134,6 +134,10 @@ Changes to the OCaml bindings
Changes to the C API
--------------------
* Add ``LLVMGetCastOpcode`` function to aid users of ``LLVMBuildCast`` in
resolving the best cast operation given a source value and destination type.
This function is a direct wrapper of ``CastInst::getCastOpcode``.
Changes to the Go bindings
--------------------------

View File

@ -3978,6 +3978,9 @@ LLVMValueRef LLVMBuildFPCast(LLVMBuilderRef, LLVMValueRef Val,
LLVMValueRef LLVMBuildIntCast(LLVMBuilderRef, LLVMValueRef Val, /*Signed cast!*/
LLVMTypeRef DestTy, const char *Name);
LLVMOpcode LLVMGetCastOpcode(LLVMValueRef Src, LLVMBool SrcIsSigned,
LLVMTypeRef DestTy, LLVMBool DestIsSigned);
/* Comparisons */
LLVMValueRef LLVMBuildICmp(LLVMBuilderRef, LLVMIntPredicate Op,
LLVMValueRef LHS, LLVMValueRef RHS,

View File

@ -3921,6 +3921,12 @@ LLVMValueRef LLVMBuildFPCast(LLVMBuilderRef B, LLVMValueRef Val,
return wrap(unwrap(B)->CreateFPCast(unwrap(Val), unwrap(DestTy), Name));
}
LLVMOpcode LLVMGetCastOpcode(LLVMValueRef Src, LLVMBool SrcIsSigned,
LLVMTypeRef DestTy, LLVMBool DestIsSigned) {
return map_to_llvmopcode(CastInst::getCastOpcode(
unwrap(Src), SrcIsSigned, unwrap(DestTy), DestIsSigned));
}
/*--.. Comparisons .........................................................--*/
LLVMValueRef LLVMBuildICmp(LLVMBuilderRef B, LLVMIntPredicate Op,

View File

@ -26,6 +26,7 @@
#include "llvm/IR/NoFolder.h"
#include "llvm/IR/Operator.h"
#include "llvm/Support/SourceMgr.h"
#include "llvm-c/Core.h"
#include "gmock/gmock-matchers.h"
#include "gtest/gtest.h"
#include <memory>
@ -391,6 +392,67 @@ TEST(InstructionsTest, CastInst) {
delete BB;
}
TEST(InstructionsTest, CastCAPI) {
LLVMContext C;
Type *Int8Ty = Type::getInt8Ty(C);
Type *Int32Ty = Type::getInt32Ty(C);
Type *Int64Ty = Type::getInt64Ty(C);
Type *FloatTy = Type::getFloatTy(C);
Type *DoubleTy = Type::getDoubleTy(C);
Type *Int8PtrTy = PointerType::get(Int8Ty, 0);
Type *Int32PtrTy = PointerType::get(Int32Ty, 0);
const Constant *C8 = Constant::getNullValue(Int8Ty);
const Constant *C64 = Constant::getNullValue(Int64Ty);
EXPECT_EQ(LLVMBitCast,
LLVMGetCastOpcode(wrap(C64), true, wrap(Int64Ty), true));
EXPECT_EQ(LLVMTrunc, LLVMGetCastOpcode(wrap(C64), true, wrap(Int8Ty), true));
EXPECT_EQ(LLVMSExt, LLVMGetCastOpcode(wrap(C8), true, wrap(Int64Ty), true));
EXPECT_EQ(LLVMZExt, LLVMGetCastOpcode(wrap(C8), false, wrap(Int64Ty), true));
const Constant *CF32 = Constant::getNullValue(FloatTy);
const Constant *CF64 = Constant::getNullValue(DoubleTy);
EXPECT_EQ(LLVMFPToUI,
LLVMGetCastOpcode(wrap(CF32), true, wrap(Int8Ty), false));
EXPECT_EQ(LLVMFPToSI,
LLVMGetCastOpcode(wrap(CF32), true, wrap(Int8Ty), true));
EXPECT_EQ(LLVMUIToFP,
LLVMGetCastOpcode(wrap(C8), false, wrap(FloatTy), true));
EXPECT_EQ(LLVMSIToFP, LLVMGetCastOpcode(wrap(C8), true, wrap(FloatTy), true));
EXPECT_EQ(LLVMFPTrunc,
LLVMGetCastOpcode(wrap(CF64), true, wrap(FloatTy), true));
EXPECT_EQ(LLVMFPExt,
LLVMGetCastOpcode(wrap(CF32), true, wrap(DoubleTy), true));
const Constant *CPtr8 = Constant::getNullValue(Int8PtrTy);
EXPECT_EQ(LLVMPtrToInt,
LLVMGetCastOpcode(wrap(CPtr8), true, wrap(Int8Ty), true));
EXPECT_EQ(LLVMIntToPtr,
LLVMGetCastOpcode(wrap(C8), true, wrap(Int8PtrTy), true));
Type *V8x8Ty = FixedVectorType::get(Int8Ty, 8);
Type *V8x64Ty = FixedVectorType::get(Int64Ty, 8);
const Constant *CV8 = Constant::getNullValue(V8x8Ty);
const Constant *CV64 = Constant::getNullValue(V8x64Ty);
EXPECT_EQ(LLVMTrunc, LLVMGetCastOpcode(wrap(CV64), true, wrap(V8x8Ty), true));
EXPECT_EQ(LLVMSExt, LLVMGetCastOpcode(wrap(CV8), true, wrap(V8x64Ty), true));
Type *Int32PtrAS1Ty = PointerType::get(Int32Ty, 1);
Type *V2Int32PtrAS1Ty = FixedVectorType::get(Int32PtrAS1Ty, 2);
Type *V2Int32PtrTy = FixedVectorType::get(Int32PtrTy, 2);
const Constant *CV2ptr32 = Constant::getNullValue(V2Int32PtrTy);
EXPECT_EQ(LLVMAddrSpaceCast, LLVMGetCastOpcode(wrap(CV2ptr32), true,
wrap(V2Int32PtrAS1Ty), true));
}
TEST(InstructionsTest, VectorGep) {
LLVMContext C;