Modify the intrinsics pattern to separate out the "return" types from the

"parameter" types. An intrinsic can now return a multiple return values like
this:

  def add_with_overflow : Intrinsic<[llvm_i32_ty, llvm_i1_ty],
                                    [LLVMMatchType<0>, LLVMMatchType<0>]>;



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@59237 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Bill Wendling 2008-11-13 09:08:33 +00:00
parent 3c902e81fa
commit cdcc3e6e12
11 changed files with 782 additions and 644 deletions

View File

@ -117,16 +117,20 @@ def llvm_vararg_ty : LLVMType<isVoid>; // this means vararg here
// name with the "llvm." prefix removed, and all "."s turned into "_"s. For // name with the "llvm." prefix removed, and all "."s turned into "_"s. For
// example, llvm.bswap.i16 -> int_bswap_i16. // example, llvm.bswap.i16 -> int_bswap_i16.
// //
// * Types is a list containing the return type and the argument types // * RetTypes is a list containing the return types expected for the
// expected for the intrinsic. // intrinsic.
// * ParamTypes is a list containing the parameter types expected for the
// intrinsic.
// * Properties can be set to describe the behavior of the intrinsic. // * Properties can be set to describe the behavior of the intrinsic.
// //
class Intrinsic<list<LLVMType> types, class Intrinsic<list<LLVMType> ret_types,
list<LLVMType> param_types = [],
list<IntrinsicProperty> properties = [], list<IntrinsicProperty> properties = [],
string name = ""> { string name = ""> {
string LLVMName = name; string LLVMName = name;
string TargetPrefix = ""; // Set to a prefix for target-specific intrinsics. string TargetPrefix = ""; // Set to a prefix for target-specific intrinsics.
list<LLVMType> Types = types; list<LLVMType> RetTypes = ret_types;
list<LLVMType> ParamTypes = param_types;
list<IntrinsicProperty> Properties = properties; list<IntrinsicProperty> Properties = properties;
} }
@ -141,64 +145,71 @@ class GCCBuiltin<string name> {
//===--------------- Variable Argument Handling Intrinsics ----------------===// //===--------------- Variable Argument Handling Intrinsics ----------------===//
// //
def int_vastart : Intrinsic<[llvm_void_ty, llvm_ptr_ty], [], "llvm.va_start">; def int_vastart : Intrinsic<[llvm_void_ty], [llvm_ptr_ty], [], "llvm.va_start">;
def int_vacopy : Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_ptr_ty], [], def int_vacopy : Intrinsic<[llvm_void_ty], [llvm_ptr_ty, llvm_ptr_ty], [],
"llvm.va_copy">; "llvm.va_copy">;
def int_vaend : Intrinsic<[llvm_void_ty, llvm_ptr_ty], [], "llvm.va_end">; def int_vaend : Intrinsic<[llvm_void_ty], [llvm_ptr_ty], [], "llvm.va_end">;
//===------------------- Garbage Collection Intrinsics --------------------===// //===------------------- Garbage Collection Intrinsics --------------------===//
// //
def int_gcroot : Intrinsic<[llvm_void_ty, llvm_ptrptr_ty, llvm_ptr_ty]>; def int_gcroot : Intrinsic<[llvm_void_ty], [llvm_ptrptr_ty, llvm_ptr_ty]>;
def int_gcread : Intrinsic<[llvm_ptr_ty, llvm_ptr_ty, llvm_ptrptr_ty], def int_gcread : Intrinsic<[llvm_ptr_ty], [llvm_ptr_ty, llvm_ptrptr_ty],
[IntrReadArgMem]>; [IntrReadArgMem]>;
def int_gcwrite : Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_ptr_ty, def int_gcwrite : Intrinsic<[llvm_void_ty], [llvm_ptr_ty, llvm_ptr_ty,
llvm_ptrptr_ty], [IntrWriteArgMem]>; llvm_ptrptr_ty], [IntrWriteArgMem]>;
//===--------------------- Code Generator Intrinsics ----------------------===// //===--------------------- Code Generator Intrinsics ----------------------===//
// //
def int_returnaddress : Intrinsic<[llvm_ptr_ty, llvm_i32_ty], [IntrNoMem]>; def int_returnaddress : Intrinsic<[llvm_ptr_ty], [llvm_i32_ty], [IntrNoMem]>;
def int_frameaddress : Intrinsic<[llvm_ptr_ty, llvm_i32_ty], [IntrNoMem]>; def int_frameaddress : Intrinsic<[llvm_ptr_ty], [llvm_i32_ty], [IntrNoMem]>;
// Note: we treat stacksave/stackrestore as writemem because we don't otherwise // Note: we treat stacksave/stackrestore as writemem because we don't otherwise
// model their dependencies on allocas. // model their dependencies on allocas.
def int_stacksave : Intrinsic<[llvm_ptr_ty]>, def int_stacksave : Intrinsic<[llvm_ptr_ty]>,
GCCBuiltin<"__builtin_stack_save">; GCCBuiltin<"__builtin_stack_save">;
def int_stackrestore : Intrinsic<[llvm_void_ty, llvm_ptr_ty]>, def int_stackrestore : Intrinsic<[llvm_void_ty], [llvm_ptr_ty]>,
GCCBuiltin<"__builtin_stack_restore">; GCCBuiltin<"__builtin_stack_restore">;
// IntrWriteArgMem is more pessimistic than strictly necessary for prefetch, // IntrWriteArgMem is more pessimistic than strictly necessary for prefetch,
// however it does conveniently prevent the prefetch from being reordered // however it does conveniently prevent the prefetch from being reordered
// with respect to nearby accesses to the same memory. // with respect to nearby accesses to the same memory.
def int_prefetch : Intrinsic<[llvm_void_ty, llvm_ptr_ty, def int_prefetch : Intrinsic<[llvm_void_ty],
llvm_i32_ty, llvm_i32_ty], [llvm_ptr_ty, llvm_i32_ty, llvm_i32_ty],
[IntrWriteArgMem]>; [IntrWriteArgMem]>;
def int_pcmarker : Intrinsic<[llvm_void_ty, llvm_i32_ty]>; def int_pcmarker : Intrinsic<[llvm_void_ty], [llvm_i32_ty]>;
def int_readcyclecounter : Intrinsic<[llvm_i64_ty]>; def int_readcyclecounter : Intrinsic<[llvm_i64_ty]>;
// Stack Protector Intrinsics - The stackprotector_create writes the stack guard // Stack Protector Intrinsics - The stackprotector_create writes the stack guard
// to the correct place on the stack frame. The stackprotector_check reads back // to the correct place on the stack frame. The stackprotector_check reads back
// the stack guard that the stackprotector_create stored. // the stack guard that the stackprotector_create stored.
def int_stackprotector_create : Intrinsic<[llvm_void_ty, llvm_ptr_ty, def int_stackprotector_create : Intrinsic<[llvm_void_ty],
llvm_ptrptr_ty], [IntrWriteMem]>; [llvm_ptr_ty, llvm_ptrptr_ty],
def int_stackprotector_check : Intrinsic<[llvm_ptr_ty, llvm_ptrptr_ty], [IntrWriteMem]>;
def int_stackprotector_check : Intrinsic<[llvm_ptr_ty], [llvm_ptrptr_ty],
[IntrReadMem]>; [IntrReadMem]>;
//===------------------- Standard C Library Intrinsics --------------------===// //===------------------- Standard C Library Intrinsics --------------------===//
// //
let Properties = [IntrWriteArgMem] in { let Properties = [IntrWriteArgMem] in {
def int_memcpy_i32 : Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_ptr_ty, def int_memcpy_i32 : Intrinsic<[llvm_void_ty],
[llvm_ptr_ty, llvm_ptr_ty,
llvm_i32_ty, llvm_i32_ty]>; llvm_i32_ty, llvm_i32_ty]>;
def int_memcpy_i64 : Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_ptr_ty, def int_memcpy_i64 : Intrinsic<[llvm_void_ty],
[llvm_ptr_ty, llvm_ptr_ty,
llvm_i64_ty, llvm_i32_ty]>; llvm_i64_ty, llvm_i32_ty]>;
def int_memmove_i32 : Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_ptr_ty, def int_memmove_i32 : Intrinsic<[llvm_void_ty],
[llvm_ptr_ty, llvm_ptr_ty,
llvm_i32_ty, llvm_i32_ty]>; llvm_i32_ty, llvm_i32_ty]>;
def int_memmove_i64 : Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_ptr_ty, def int_memmove_i64 : Intrinsic<[llvm_void_ty],
[llvm_ptr_ty, llvm_ptr_ty,
llvm_i64_ty, llvm_i32_ty]>; llvm_i64_ty, llvm_i32_ty]>;
def int_memset_i32 : Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_i8_ty, def int_memset_i32 : Intrinsic<[llvm_void_ty],
[llvm_ptr_ty, llvm_i8_ty,
llvm_i32_ty, llvm_i32_ty]>; llvm_i32_ty, llvm_i32_ty]>;
def int_memset_i64 : Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_i8_ty, def int_memset_i64 : Intrinsic<[llvm_void_ty],
[llvm_ptr_ty, llvm_i8_ty,
llvm_i64_ty, llvm_i32_ty]>; llvm_i64_ty, llvm_i32_ty]>;
} }
@ -206,156 +217,159 @@ let Properties = [IntrWriteArgMem] in {
// rounding mode. This needs to be modelled separately; in the meantime // rounding mode. This needs to be modelled separately; in the meantime
// declaring them as reading memory is conservatively correct. // declaring them as reading memory is conservatively correct.
let Properties = [IntrReadMem] in { let Properties = [IntrReadMem] in {
def int_sqrt : Intrinsic<[llvm_anyfloat_ty, LLVMMatchType<0>]>; def int_sqrt : Intrinsic<[llvm_anyfloat_ty], [LLVMMatchType<0>]>;
def int_powi : Intrinsic<[llvm_anyfloat_ty, LLVMMatchType<0>, llvm_i32_ty]>; def int_powi : Intrinsic<[llvm_anyfloat_ty], [LLVMMatchType<0>, llvm_i32_ty]>;
def int_sin : Intrinsic<[llvm_anyfloat_ty, LLVMMatchType<0>]>; def int_sin : Intrinsic<[llvm_anyfloat_ty], [LLVMMatchType<0>]>;
def int_cos : Intrinsic<[llvm_anyfloat_ty, LLVMMatchType<0>]>; def int_cos : Intrinsic<[llvm_anyfloat_ty], [LLVMMatchType<0>]>;
def int_pow : Intrinsic<[llvm_anyfloat_ty, def int_pow : Intrinsic<[llvm_anyfloat_ty],
LLVMMatchType<0>, LLVMMatchType<0>]>; [LLVMMatchType<0>, LLVMMatchType<0>]>;
def int_log : Intrinsic<[llvm_anyfloat_ty, LLVMMatchType<0>]>; def int_log : Intrinsic<[llvm_anyfloat_ty], [LLVMMatchType<0>]>;
def int_log10: Intrinsic<[llvm_anyfloat_ty, LLVMMatchType<0>]>; def int_log10: Intrinsic<[llvm_anyfloat_ty], [LLVMMatchType<0>]>;
def int_log2 : Intrinsic<[llvm_anyfloat_ty, LLVMMatchType<0>]>; def int_log2 : Intrinsic<[llvm_anyfloat_ty], [LLVMMatchType<0>]>;
def int_exp : Intrinsic<[llvm_anyfloat_ty, LLVMMatchType<0>]>; def int_exp : Intrinsic<[llvm_anyfloat_ty], [LLVMMatchType<0>]>;
def int_exp2 : Intrinsic<[llvm_anyfloat_ty, LLVMMatchType<0>]>; def int_exp2 : Intrinsic<[llvm_anyfloat_ty], [LLVMMatchType<0>]>;
} }
// NOTE: these are internal interfaces. // NOTE: these are internal interfaces.
def int_setjmp : Intrinsic<[llvm_i32_ty , llvm_ptr_ty]>; def int_setjmp : Intrinsic<[llvm_i32_ty], [llvm_ptr_ty]>;
def int_longjmp : Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_i32_ty]>; def int_longjmp : Intrinsic<[llvm_void_ty], [llvm_ptr_ty, llvm_i32_ty]>;
def int_sigsetjmp : Intrinsic<[llvm_i32_ty , llvm_ptr_ty, llvm_i32_ty]>; def int_sigsetjmp : Intrinsic<[llvm_i32_ty] , [llvm_ptr_ty, llvm_i32_ty]>;
def int_siglongjmp : Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_i32_ty]>; def int_siglongjmp : Intrinsic<[llvm_void_ty], [llvm_ptr_ty, llvm_i32_ty]>;
//===-------------------- Bit Manipulation Intrinsics ---------------------===// //===-------------------- Bit Manipulation Intrinsics ---------------------===//
// //
// None of these intrinsics accesses memory at all. // None of these intrinsics accesses memory at all.
let Properties = [IntrNoMem] in { let Properties = [IntrNoMem] in {
def int_bswap: Intrinsic<[llvm_anyint_ty, LLVMMatchType<0>]>; def int_bswap: Intrinsic<[llvm_anyint_ty], [LLVMMatchType<0>]>;
def int_ctpop: Intrinsic<[llvm_anyint_ty, LLVMMatchType<0>]>; def int_ctpop: Intrinsic<[llvm_anyint_ty], [LLVMMatchType<0>]>;
def int_ctlz : Intrinsic<[llvm_anyint_ty, LLVMMatchType<0>]>; def int_ctlz : Intrinsic<[llvm_anyint_ty], [LLVMMatchType<0>]>;
def int_cttz : Intrinsic<[llvm_anyint_ty, LLVMMatchType<0>]>; def int_cttz : Intrinsic<[llvm_anyint_ty], [LLVMMatchType<0>]>;
def int_part_select : def int_part_select :
Intrinsic<[llvm_anyint_ty, LLVMMatchType<0>, llvm_i32_ty, llvm_i32_ty]>; Intrinsic<[llvm_anyint_ty], [LLVMMatchType<0>, llvm_i32_ty, llvm_i32_ty]>;
def int_part_set : def int_part_set :
Intrinsic<[llvm_anyint_ty, LLVMMatchType<0>, llvm_anyint_ty, llvm_i32_ty, Intrinsic<[llvm_anyint_ty],
llvm_i32_ty]>; [LLVMMatchType<0>, llvm_anyint_ty, llvm_i32_ty, llvm_i32_ty]>;
} }
//===------------------------ Debugger Intrinsics -------------------------===// //===------------------------ Debugger Intrinsics -------------------------===//
// //
def int_dbg_stoppoint : Intrinsic<[llvm_void_ty, def int_dbg_stoppoint : Intrinsic<[llvm_void_ty],
llvm_i32_ty, llvm_i32_ty, [llvm_i32_ty, llvm_i32_ty,
llvm_descriptor_ty]>; llvm_descriptor_ty]>;
def int_dbg_region_start : Intrinsic<[llvm_void_ty, llvm_descriptor_ty]>; def int_dbg_region_start : Intrinsic<[llvm_void_ty], [llvm_descriptor_ty]>;
def int_dbg_region_end : Intrinsic<[llvm_void_ty, llvm_descriptor_ty]>; def int_dbg_region_end : Intrinsic<[llvm_void_ty], [llvm_descriptor_ty]>;
def int_dbg_func_start : Intrinsic<[llvm_void_ty, llvm_descriptor_ty]>; def int_dbg_func_start : Intrinsic<[llvm_void_ty], [llvm_descriptor_ty]>;
def int_dbg_declare : Intrinsic<[llvm_void_ty, llvm_descriptor_ty, def int_dbg_declare : Intrinsic<[llvm_void_ty],
llvm_descriptor_ty]>; [llvm_descriptor_ty, llvm_descriptor_ty]>;
//===------------------ Exception Handling Intrinsics----------------------===// //===------------------ Exception Handling Intrinsics----------------------===//
// //
def int_eh_exception : Intrinsic<[llvm_ptr_ty]>; def int_eh_exception : Intrinsic<[llvm_ptr_ty]>;
def int_eh_selector_i32 : Intrinsic<[llvm_i32_ty, llvm_ptr_ty, llvm_ptr_ty, def int_eh_selector_i32 : Intrinsic<[llvm_i32_ty],
llvm_vararg_ty]>; [llvm_ptr_ty, llvm_ptr_ty, llvm_vararg_ty]>;
def int_eh_selector_i64 : Intrinsic<[llvm_i64_ty, llvm_ptr_ty, llvm_ptr_ty, def int_eh_selector_i64 : Intrinsic<[llvm_i64_ty],
llvm_vararg_ty]>; [llvm_ptr_ty, llvm_ptr_ty, llvm_vararg_ty]>;
def int_eh_typeid_for_i32 : Intrinsic<[llvm_i32_ty, llvm_ptr_ty]>; def int_eh_typeid_for_i32 : Intrinsic<[llvm_i32_ty], [llvm_ptr_ty]>;
def int_eh_typeid_for_i64 : Intrinsic<[llvm_i64_ty, llvm_ptr_ty]>; def int_eh_typeid_for_i64 : Intrinsic<[llvm_i64_ty], [llvm_ptr_ty]>;
def int_eh_return_i32 : Intrinsic<[llvm_void_ty, llvm_i32_ty, llvm_ptr_ty]>; def int_eh_return_i32 : Intrinsic<[llvm_void_ty], [llvm_i32_ty, llvm_ptr_ty]>;
def int_eh_return_i64 : Intrinsic<[llvm_void_ty, llvm_i64_ty, llvm_ptr_ty]>; def int_eh_return_i64 : Intrinsic<[llvm_void_ty], [llvm_i64_ty, llvm_ptr_ty]>;
def int_eh_unwind_init: Intrinsic<[llvm_void_ty]>, def int_eh_unwind_init: Intrinsic<[llvm_void_ty]>,
GCCBuiltin<"__builtin_unwind_init">; GCCBuiltin<"__builtin_unwind_init">;
def int_eh_dwarf_cfa : Intrinsic<[llvm_ptr_ty, llvm_i32_ty]>; def int_eh_dwarf_cfa : Intrinsic<[llvm_ptr_ty], [llvm_i32_ty]>;
//===---------------- Generic Variable Attribute Intrinsics----------------===// //===---------------- Generic Variable Attribute Intrinsics----------------===//
// //
def int_var_annotation : Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_ptr_ty, def int_var_annotation : Intrinsic<[llvm_void_ty],
[llvm_ptr_ty, llvm_ptr_ty,
llvm_ptr_ty, llvm_i32_ty], llvm_ptr_ty, llvm_i32_ty],
[], "llvm.var.annotation">; [], "llvm.var.annotation">;
def int_ptr_annotation : Intrinsic<[LLVMAnyPointerType<llvm_anyint_ty>, def int_ptr_annotation : Intrinsic<[LLVMAnyPointerType<llvm_anyint_ty>],
LLVMMatchType<0>, [LLVMMatchType<0>, llvm_ptr_ty, llvm_ptr_ty,
llvm_ptr_ty, llvm_ptr_ty, llvm_i32_ty], llvm_i32_ty],
[], "llvm.ptr.annotation">; [], "llvm.ptr.annotation">;
def int_annotation : Intrinsic<[llvm_anyint_ty, LLVMMatchType<0>, llvm_ptr_ty, def int_annotation : Intrinsic<[llvm_anyint_ty],
[LLVMMatchType<0>, llvm_ptr_ty,
llvm_ptr_ty, llvm_i32_ty], llvm_ptr_ty, llvm_i32_ty],
[], "llvm.annotation">; [], "llvm.annotation">;
//===------------------------ Trampoline Intrinsics -----------------------===// //===------------------------ Trampoline Intrinsics -----------------------===//
// //
def int_init_trampoline : Intrinsic<[llvm_ptr_ty, llvm_ptr_ty, llvm_ptr_ty, def int_init_trampoline : Intrinsic<[llvm_ptr_ty],
llvm_ptr_ty], []>, [llvm_ptr_ty, llvm_ptr_ty, llvm_ptr_ty],
[]>,
GCCBuiltin<"__builtin_init_trampoline">; GCCBuiltin<"__builtin_init_trampoline">;
//===------------------------- Atomic Intrinsics --------------------------===// //===------------------------- Atomic Intrinsics --------------------------===//
// //
def int_memory_barrier : Intrinsic<[llvm_void_ty, llvm_i1_ty, llvm_i1_ty, def int_memory_barrier : Intrinsic<[llvm_void_ty], [llvm_i1_ty, llvm_i1_ty,
llvm_i1_ty, llvm_i1_ty, llvm_i1_ty], []>, llvm_i1_ty, llvm_i1_ty, llvm_i1_ty], []>,
GCCBuiltin<"__builtin_llvm_memory_barrier">; GCCBuiltin<"__builtin_llvm_memory_barrier">;
def int_atomic_cmp_swap : Intrinsic<[llvm_anyint_ty, def int_atomic_cmp_swap : Intrinsic<[llvm_anyint_ty],
LLVMAnyPointerType<LLVMMatchType<0>>, [LLVMAnyPointerType<LLVMMatchType<0>>,
LLVMMatchType<0>, LLVMMatchType<0>], LLVMMatchType<0>, LLVMMatchType<0>],
[IntrWriteArgMem]>, [IntrWriteArgMem]>,
GCCBuiltin<"__sync_val_compare_and_swap">; GCCBuiltin<"__sync_val_compare_and_swap">;
def int_atomic_load_add : Intrinsic<[llvm_anyint_ty, def int_atomic_load_add : Intrinsic<[llvm_anyint_ty],
LLVMAnyPointerType<LLVMMatchType<0>>, [LLVMAnyPointerType<LLVMMatchType<0>>,
LLVMMatchType<0>], LLVMMatchType<0>],
[IntrWriteArgMem]>, [IntrWriteArgMem]>,
GCCBuiltin<"__sync_fetch_and_add">; GCCBuiltin<"__sync_fetch_and_add">;
def int_atomic_swap : Intrinsic<[llvm_anyint_ty, def int_atomic_swap : Intrinsic<[llvm_anyint_ty],
LLVMAnyPointerType<LLVMMatchType<0>>, [LLVMAnyPointerType<LLVMMatchType<0>>,
LLVMMatchType<0>], LLVMMatchType<0>],
[IntrWriteArgMem]>, [IntrWriteArgMem]>,
GCCBuiltin<"__sync_lock_test_and_set">; GCCBuiltin<"__sync_lock_test_and_set">;
def int_atomic_load_sub : Intrinsic<[llvm_anyint_ty, def int_atomic_load_sub : Intrinsic<[llvm_anyint_ty],
LLVMAnyPointerType<LLVMMatchType<0>>, [LLVMAnyPointerType<LLVMMatchType<0>>,
LLVMMatchType<0>], LLVMMatchType<0>],
[IntrWriteArgMem]>, [IntrWriteArgMem]>,
GCCBuiltin<"__sync_fetch_and_sub">; GCCBuiltin<"__sync_fetch_and_sub">;
def int_atomic_load_and : Intrinsic<[llvm_anyint_ty, def int_atomic_load_and : Intrinsic<[llvm_anyint_ty],
LLVMAnyPointerType<LLVMMatchType<0>>, [LLVMAnyPointerType<LLVMMatchType<0>>,
LLVMMatchType<0>], LLVMMatchType<0>],
[IntrWriteArgMem]>, [IntrWriteArgMem]>,
GCCBuiltin<"__sync_fetch_and_and">; GCCBuiltin<"__sync_fetch_and_and">;
def int_atomic_load_or : Intrinsic<[llvm_anyint_ty, def int_atomic_load_or : Intrinsic<[llvm_anyint_ty],
LLVMAnyPointerType<LLVMMatchType<0>>, [LLVMAnyPointerType<LLVMMatchType<0>>,
LLVMMatchType<0>], LLVMMatchType<0>],
[IntrWriteArgMem]>, [IntrWriteArgMem]>,
GCCBuiltin<"__sync_fetch_and_or">; GCCBuiltin<"__sync_fetch_and_or">;
def int_atomic_load_xor : Intrinsic<[llvm_anyint_ty, def int_atomic_load_xor : Intrinsic<[llvm_anyint_ty],
LLVMAnyPointerType<LLVMMatchType<0>>, [LLVMAnyPointerType<LLVMMatchType<0>>,
LLVMMatchType<0>], LLVMMatchType<0>],
[IntrWriteArgMem]>, [IntrWriteArgMem]>,
GCCBuiltin<"__sync_fetch_and_xor">; GCCBuiltin<"__sync_fetch_and_xor">;
def int_atomic_load_nand : Intrinsic<[llvm_anyint_ty, def int_atomic_load_nand : Intrinsic<[llvm_anyint_ty],
LLVMAnyPointerType<LLVMMatchType<0>>, [LLVMAnyPointerType<LLVMMatchType<0>>,
LLVMMatchType<0>], LLVMMatchType<0>],
[IntrWriteArgMem]>, [IntrWriteArgMem]>,
GCCBuiltin<"__sync_fetch_and_nand">; GCCBuiltin<"__sync_fetch_and_nand">;
def int_atomic_load_min : Intrinsic<[llvm_anyint_ty, def int_atomic_load_min : Intrinsic<[llvm_anyint_ty],
LLVMAnyPointerType<LLVMMatchType<0>>, [LLVMAnyPointerType<LLVMMatchType<0>>,
LLVMMatchType<0>], LLVMMatchType<0>],
[IntrWriteArgMem]>, [IntrWriteArgMem]>,
GCCBuiltin<"__sync_fetch_and_min">; GCCBuiltin<"__sync_fetch_and_min">;
def int_atomic_load_max : Intrinsic<[llvm_anyint_ty, def int_atomic_load_max : Intrinsic<[llvm_anyint_ty],
LLVMAnyPointerType<LLVMMatchType<0>>, [LLVMAnyPointerType<LLVMMatchType<0>>,
LLVMMatchType<0>], LLVMMatchType<0>],
[IntrWriteArgMem]>, [IntrWriteArgMem]>,
GCCBuiltin<"__sync_fetch_and_max">; GCCBuiltin<"__sync_fetch_and_max">;
def int_atomic_load_umin : Intrinsic<[llvm_anyint_ty, def int_atomic_load_umin : Intrinsic<[llvm_anyint_ty],
LLVMAnyPointerType<LLVMMatchType<0>>, [LLVMAnyPointerType<LLVMMatchType<0>>,
LLVMMatchType<0>], LLVMMatchType<0>],
[IntrWriteArgMem]>, [IntrWriteArgMem]>,
GCCBuiltin<"__sync_fetch_and_umin">; GCCBuiltin<"__sync_fetch_and_umin">;
def int_atomic_load_umax : Intrinsic<[llvm_anyint_ty, def int_atomic_load_umax : Intrinsic<[llvm_anyint_ty],
LLVMAnyPointerType<LLVMMatchType<0>>, [LLVMAnyPointerType<LLVMMatchType<0>>,
LLVMMatchType<0>], LLVMMatchType<0>],
[IntrWriteArgMem]>, [IntrWriteArgMem]>,
GCCBuiltin<"__sync_fetch_and_umax">; GCCBuiltin<"__sync_fetch_and_umax">;
//===-------------------------- Other Intrinsics --------------------------===// //===-------------------------- Other Intrinsics --------------------------===//
@ -369,24 +383,24 @@ def int_trap : Intrinsic<[llvm_void_ty]>,
// various types with rounding and saturation. NOTE: avoid using these // various types with rounding and saturation. NOTE: avoid using these
// intrinsics as they might be removed sometime in the future and // intrinsics as they might be removed sometime in the future and
// most targets don't support them. // most targets don't support them.
def int_convertff : Intrinsic<[llvm_anyfloat_ty, llvm_anyfloat_ty, def int_convertff : Intrinsic<[llvm_anyfloat_ty],
llvm_i32_ty, llvm_i32_ty]>; [llvm_anyfloat_ty, llvm_i32_ty, llvm_i32_ty]>;
def int_convertfsi : Intrinsic<[llvm_anyfloat_ty, llvm_anyint_ty, def int_convertfsi : Intrinsic<[llvm_anyfloat_ty],
llvm_i32_ty, llvm_i32_ty]>; [llvm_anyint_ty, llvm_i32_ty, llvm_i32_ty]>;
def int_convertfui : Intrinsic<[llvm_anyfloat_ty, llvm_anyint_ty, def int_convertfui : Intrinsic<[llvm_anyfloat_ty],
llvm_i32_ty, llvm_i32_ty]>; [llvm_anyint_ty, llvm_i32_ty, llvm_i32_ty]>;
def int_convertsif : Intrinsic<[llvm_anyint_ty, llvm_anyfloat_ty, def int_convertsif : Intrinsic<[llvm_anyint_ty],
llvm_i32_ty, llvm_i32_ty]>; [llvm_anyfloat_ty, llvm_i32_ty, llvm_i32_ty]>;
def int_convertuif : Intrinsic<[llvm_anyint_ty, llvm_anyfloat_ty, def int_convertuif : Intrinsic<[llvm_anyint_ty],
llvm_i32_ty, llvm_i32_ty]>; [llvm_anyfloat_ty, llvm_i32_ty, llvm_i32_ty]>;
def int_convertss : Intrinsic<[llvm_anyint_ty, llvm_anyint_ty, def int_convertss : Intrinsic<[llvm_anyint_ty],
llvm_i32_ty, llvm_i32_ty]>; [llvm_anyint_ty, llvm_i32_ty, llvm_i32_ty]>;
def int_convertsu : Intrinsic<[llvm_anyint_ty, llvm_anyint_ty, def int_convertsu : Intrinsic<[llvm_anyint_ty],
llvm_i32_ty, llvm_i32_ty]>; [llvm_anyint_ty, llvm_i32_ty, llvm_i32_ty]>;
def int_convertus : Intrinsic<[llvm_anyint_ty, llvm_anyint_ty, def int_convertus : Intrinsic<[llvm_anyint_ty],
llvm_i32_ty, llvm_i32_ty]>; [llvm_anyint_ty, llvm_i32_ty, llvm_i32_ty]>;
def int_convertuu : Intrinsic<[llvm_anyint_ty, llvm_anyint_ty, def int_convertuu : Intrinsic<[llvm_anyint_ty],
llvm_i32_ty, llvm_i32_ty]>; [llvm_anyint_ty, llvm_i32_ty, llvm_i32_ty]>;
//===----------------------------------------------------------------------===// //===----------------------------------------------------------------------===//
// Target-specific intrinsics // Target-specific intrinsics

View File

@ -17,5 +17,5 @@
let TargetPrefix = "arm" in { // All intrinsics start with "llvm.arm.". let TargetPrefix = "arm" in { // All intrinsics start with "llvm.arm.".
def int_arm_thread_pointer : GCCBuiltin<"__builtin_thread_pointer">, def int_arm_thread_pointer : GCCBuiltin<"__builtin_thread_pointer">,
Intrinsic<[llvm_ptr_ty],[IntrNoMem]>; Intrinsic<[llvm_ptr_ty], [], [IntrNoMem]>;
} }

View File

@ -14,6 +14,5 @@
let TargetPrefix = "alpha" in { // All intrinsics start with "llvm.alpha.". let TargetPrefix = "alpha" in { // All intrinsics start with "llvm.alpha.".
def int_alpha_umulh : GCCBuiltin<"__builtin_alpha_umulh">, def int_alpha_umulh : GCCBuiltin<"__builtin_alpha_umulh">,
Intrinsic<[llvm_i64_ty, llvm_i64_ty, llvm_i64_ty], [IntrNoMem]>; Intrinsic<[llvm_i64_ty], [llvm_i64_ty, llvm_i64_ty], [IntrNoMem]>;
} }

View File

@ -25,77 +25,77 @@ def llvm_i128_ty : LLVMType<i128>;
class v16i8_u7imm<string builtin_suffix> : class v16i8_u7imm<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v16i8_ty, llvm_v16i8_ty, cell_i7_ty], Intrinsic<[llvm_v16i8_ty], [llvm_v16i8_ty, cell_i7_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v16i8_u8imm<string builtin_suffix> : class v16i8_u8imm<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v16i8_ty, llvm_v16i8_ty, llvm_i8_ty], Intrinsic<[llvm_v16i8_ty], [llvm_v16i8_ty, llvm_i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v16i8_s10imm<string builtin_suffix> : class v16i8_s10imm<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v16i8_ty, llvm_v16i8_ty, llvm_i16_ty], Intrinsic<[llvm_v16i8_ty], [llvm_v16i8_ty, llvm_i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v16i8_u16imm<string builtin_suffix> : class v16i8_u16imm<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v16i8_ty, llvm_v16i8_ty, llvm_i16_ty], Intrinsic<[llvm_v16i8_ty], [llvm_v16i8_ty, llvm_i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v16i8_rr<string builtin_suffix> : class v16i8_rr<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v16i8_ty, llvm_v16i8_ty, llvm_v16i8_ty], Intrinsic<[llvm_v16i8_ty], [llvm_v16i8_ty, llvm_v16i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v8i16_s10imm<string builtin_suffix> : class v8i16_s10imm<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v8i16_ty, llvm_v8i16_ty, llvm_i16_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v8i16_ty, llvm_i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v8i16_u16imm<string builtin_suffix> : class v8i16_u16imm<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v8i16_ty, llvm_v8i16_ty, llvm_i16_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v8i16_ty, llvm_i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v8i16_rr<string builtin_suffix> : class v8i16_rr<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v8i16_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v4i32_rr<string builtin_suffix> : class v4i32_rr<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v4i32_ty, llvm_v4i32_ty, llvm_v4i32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4i32_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v4i32_u7imm<string builtin_suffix> : class v4i32_u7imm<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v4i32_ty, llvm_v4i32_ty, cell_i7_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4i32_ty, cell_i7_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v4i32_s10imm<string builtin_suffix> : class v4i32_s10imm<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v4i32_ty, llvm_v4i32_ty, llvm_i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4i32_ty, llvm_i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v4i32_u16imm<string builtin_suffix> : class v4i32_u16imm<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v4i32_ty, llvm_v4i32_ty, llvm_i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4i32_ty, llvm_i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v4f32_rr<string builtin_suffix> : class v4f32_rr<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v4f32_ty, llvm_v4f32_ty, llvm_v4f32_ty], Intrinsic<[llvm_v4f32_ty], [llvm_v4f32_ty, llvm_v4f32_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v4f32_rrr<string builtin_suffix> : class v4f32_rrr<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v4f32_ty, llvm_v4f32_ty, llvm_v4f32_ty, llvm_v4f32_ty], Intrinsic<[llvm_v4f32_ty], [llvm_v4f32_ty, llvm_v4f32_ty, llvm_v4f32_ty],
[IntrNoMem]>; [IntrNoMem]>;
class v2f64_rr<string builtin_suffix> : class v2f64_rr<string builtin_suffix> :
GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>, GCCBuiltin<!strconcat("__builtin_si_", builtin_suffix)>,
Intrinsic<[llvm_v2f64_ty, llvm_v2f64_ty, llvm_v2f64_ty], Intrinsic<[llvm_v2f64_ty], [llvm_v2f64_ty, llvm_v2f64_ty],
[IntrNoMem]>; [IntrNoMem]>;
// All Cell SPU intrinsics start with "llvm.spu.". // All Cell SPU intrinsics start with "llvm.spu.".
@ -117,60 +117,60 @@ let TargetPrefix = "spu" in {
def int_spu_si_bgx : v4i32_rr<"bgx">; def int_spu_si_bgx : v4i32_rr<"bgx">;
def int_spu_si_mpy : // This is special: def int_spu_si_mpy : // This is special:
GCCBuiltin<"__builtin_si_mpy">, GCCBuiltin<"__builtin_si_mpy">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_mpyu : // This is special: def int_spu_si_mpyu : // This is special:
GCCBuiltin<"__builtin_si_mpyu">, GCCBuiltin<"__builtin_si_mpyu">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_mpyi : // This is special: def int_spu_si_mpyi : // This is special:
GCCBuiltin<"__builtin_si_mpyi">, GCCBuiltin<"__builtin_si_mpyi">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_mpyui : // This is special: def int_spu_si_mpyui : // This is special:
GCCBuiltin<"__builtin_si_mpyui">, GCCBuiltin<"__builtin_si_mpyui">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_mpya : // This is special: def int_spu_si_mpya : // This is special:
GCCBuiltin<"__builtin_si_mpya">, GCCBuiltin<"__builtin_si_mpya">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_mpyh : // This is special: def int_spu_si_mpyh : // This is special:
GCCBuiltin<"__builtin_si_mpyh">, GCCBuiltin<"__builtin_si_mpyh">,
Intrinsic<[llvm_v4i32_ty, llvm_v4i32_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4i32_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_mpys : // This is special: def int_spu_si_mpys : // This is special:
GCCBuiltin<"__builtin_si_mpys">, GCCBuiltin<"__builtin_si_mpys">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_mpyhh : // This is special: def int_spu_si_mpyhh : // This is special:
GCCBuiltin<"__builtin_si_mpyhh">, GCCBuiltin<"__builtin_si_mpyhh">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_mpyhha : // This is special: def int_spu_si_mpyhha : // This is special:
GCCBuiltin<"__builtin_si_mpyhha">, GCCBuiltin<"__builtin_si_mpyhha">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_mpyhhu : // This is special: def int_spu_si_mpyhhu : // This is special:
GCCBuiltin<"__builtin_si_mpyhhu">, GCCBuiltin<"__builtin_si_mpyhhu">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_mpyhhau : // This is special: def int_spu_si_mpyhhau : // This is special:
GCCBuiltin<"__builtin_si_mpyhhau">, GCCBuiltin<"__builtin_si_mpyhhau">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_shli: v4i32_u7imm<"shli">; def int_spu_si_shli: v4i32_u7imm<"shli">;
def int_spu_si_shlqbi: def int_spu_si_shlqbi:
GCCBuiltin<!strconcat("__builtin_si_", "shlqbi")>, GCCBuiltin<!strconcat("__builtin_si_", "shlqbi")>,
Intrinsic<[llvm_v8i16_ty, llvm_v8i16_ty, llvm_i32_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v8i16_ty, llvm_i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_shlqbii: v16i8_u7imm<"shlqbii">; def int_spu_si_shlqbii: v16i8_u7imm<"shlqbii">;
def int_spu_si_shlqby: def int_spu_si_shlqby:
GCCBuiltin<!strconcat("__builtin_si_", "shlqby")>, GCCBuiltin<!strconcat("__builtin_si_", "shlqby")>,
Intrinsic<[llvm_v8i16_ty, llvm_v8i16_ty, llvm_i32_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v8i16_ty, llvm_i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_spu_si_shlqbyi: v16i8_u7imm<"shlqbyi">; def int_spu_si_shlqbyi: v16i8_u7imm<"shlqbyi">;

View File

@ -18,26 +18,27 @@
// Non-altivec intrinsics. // Non-altivec intrinsics.
let TargetPrefix = "ppc" in { // All intrinsics start with "llvm.ppc.". let TargetPrefix = "ppc" in { // All intrinsics start with "llvm.ppc.".
// dcba/dcbf/dcbi/dcbst/dcbt/dcbz/dcbzl(PPC970) instructions. // dcba/dcbf/dcbi/dcbst/dcbt/dcbz/dcbzl(PPC970) instructions.
def int_ppc_dcba : Intrinsic<[llvm_void_ty, llvm_ptr_ty], [IntrWriteMem]>; def int_ppc_dcba : Intrinsic<[llvm_void_ty], [llvm_ptr_ty], [IntrWriteMem]>;
def int_ppc_dcbf : Intrinsic<[llvm_void_ty, llvm_ptr_ty], [IntrWriteMem]>; def int_ppc_dcbf : Intrinsic<[llvm_void_ty], [llvm_ptr_ty], [IntrWriteMem]>;
def int_ppc_dcbi : Intrinsic<[llvm_void_ty, llvm_ptr_ty], [IntrWriteMem]>; def int_ppc_dcbi : Intrinsic<[llvm_void_ty], [llvm_ptr_ty], [IntrWriteMem]>;
def int_ppc_dcbst : Intrinsic<[llvm_void_ty, llvm_ptr_ty], [IntrWriteMem]>; def int_ppc_dcbst : Intrinsic<[llvm_void_ty], [llvm_ptr_ty], [IntrWriteMem]>;
def int_ppc_dcbt : Intrinsic<[llvm_void_ty, llvm_ptr_ty], [IntrWriteMem]>; def int_ppc_dcbt : Intrinsic<[llvm_void_ty], [llvm_ptr_ty], [IntrWriteMem]>;
def int_ppc_dcbtst: Intrinsic<[llvm_void_ty, llvm_ptr_ty], [IntrWriteMem]>; def int_ppc_dcbtst: Intrinsic<[llvm_void_ty], [llvm_ptr_ty], [IntrWriteMem]>;
def int_ppc_dcbz : Intrinsic<[llvm_void_ty, llvm_ptr_ty], [IntrWriteMem]>; def int_ppc_dcbz : Intrinsic<[llvm_void_ty], [llvm_ptr_ty], [IntrWriteMem]>;
def int_ppc_dcbzl : Intrinsic<[llvm_void_ty, llvm_ptr_ty], [IntrWriteMem]>; def int_ppc_dcbzl : Intrinsic<[llvm_void_ty], [llvm_ptr_ty], [IntrWriteMem]>;
// sync instruction // sync instruction
def int_ppc_sync : Intrinsic<[llvm_void_ty], [IntrWriteMem]>; def int_ppc_sync : Intrinsic<[llvm_void_ty], [], [IntrWriteMem]>;
} }
let TargetPrefix = "ppc" in { // All PPC intrinsics start with "llvm.ppc.". let TargetPrefix = "ppc" in { // All PPC intrinsics start with "llvm.ppc.".
/// PowerPC_Vec_Intrinsic - Base class for all altivec intrinsics. /// PowerPC_Vec_Intrinsic - Base class for all altivec intrinsics.
class PowerPC_Vec_Intrinsic<string GCCIntSuffix, list<LLVMType> types, class PowerPC_Vec_Intrinsic<string GCCIntSuffix, list<LLVMType> ret_types,
list<LLVMType> param_types,
list<IntrinsicProperty> properties> list<IntrinsicProperty> properties>
: GCCBuiltin<!strconcat("__builtin_altivec_", GCCIntSuffix)>, : GCCBuiltin<!strconcat("__builtin_altivec_", GCCIntSuffix)>,
Intrinsic<types, properties>; Intrinsic<ret_types, param_types, properties>;
} }
//===----------------------------------------------------------------------===// //===----------------------------------------------------------------------===//
@ -48,34 +49,34 @@ let TargetPrefix = "ppc" in { // All PPC intrinsics start with "llvm.ppc.".
/// vector and returns one. These intrinsics have no side effects. /// vector and returns one. These intrinsics have no side effects.
class PowerPC_Vec_FF_Intrinsic<string GCCIntSuffix> class PowerPC_Vec_FF_Intrinsic<string GCCIntSuffix>
: PowerPC_Vec_Intrinsic<GCCIntSuffix, : PowerPC_Vec_Intrinsic<GCCIntSuffix,
[llvm_v4f32_ty, llvm_v4f32_ty], [IntrNoMem]>; [llvm_v4f32_ty], [llvm_v4f32_ty], [IntrNoMem]>;
/// PowerPC_Vec_FFF_Intrinsic - A PowerPC intrinsic that takes two v4f32 /// PowerPC_Vec_FFF_Intrinsic - A PowerPC intrinsic that takes two v4f32
/// vectors and returns one. These intrinsics have no side effects. /// vectors and returns one. These intrinsics have no side effects.
class PowerPC_Vec_FFF_Intrinsic<string GCCIntSuffix> class PowerPC_Vec_FFF_Intrinsic<string GCCIntSuffix>
: PowerPC_Vec_Intrinsic<GCCIntSuffix, : PowerPC_Vec_Intrinsic<GCCIntSuffix,
[llvm_v4f32_ty, llvm_v4f32_ty, llvm_v4f32_ty], [llvm_v4f32_ty], [llvm_v4f32_ty, llvm_v4f32_ty],
[IntrNoMem]>; [IntrNoMem]>;
/// PowerPC_Vec_BBB_Intrinsic - A PowerPC intrinsic that takes two v16f8 /// PowerPC_Vec_BBB_Intrinsic - A PowerPC intrinsic that takes two v16f8
/// vectors and returns one. These intrinsics have no side effects. /// vectors and returns one. These intrinsics have no side effects.
class PowerPC_Vec_BBB_Intrinsic<string GCCIntSuffix> class PowerPC_Vec_BBB_Intrinsic<string GCCIntSuffix>
: PowerPC_Vec_Intrinsic<GCCIntSuffix, : PowerPC_Vec_Intrinsic<GCCIntSuffix,
[llvm_v16i8_ty, llvm_v16i8_ty, llvm_v16i8_ty], [llvm_v16i8_ty], [llvm_v16i8_ty, llvm_v16i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
/// PowerPC_Vec_HHH_Intrinsic - A PowerPC intrinsic that takes two v8i16 /// PowerPC_Vec_HHH_Intrinsic - A PowerPC intrinsic that takes two v8i16
/// vectors and returns one. These intrinsics have no side effects. /// vectors and returns one. These intrinsics have no side effects.
class PowerPC_Vec_HHH_Intrinsic<string GCCIntSuffix> class PowerPC_Vec_HHH_Intrinsic<string GCCIntSuffix>
: PowerPC_Vec_Intrinsic<GCCIntSuffix, : PowerPC_Vec_Intrinsic<GCCIntSuffix,
[llvm_v8i16_ty, llvm_v8i16_ty, llvm_v8i16_ty], [llvm_v8i16_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
/// PowerPC_Vec_WWW_Intrinsic - A PowerPC intrinsic that takes two v4i32 /// PowerPC_Vec_WWW_Intrinsic - A PowerPC intrinsic that takes two v4i32
/// vectors and returns one. These intrinsics have no side effects. /// vectors and returns one. These intrinsics have no side effects.
class PowerPC_Vec_WWW_Intrinsic<string GCCIntSuffix> class PowerPC_Vec_WWW_Intrinsic<string GCCIntSuffix>
: PowerPC_Vec_Intrinsic<GCCIntSuffix, : PowerPC_Vec_Intrinsic<GCCIntSuffix,
[llvm_v4i32_ty, llvm_v4i32_ty, llvm_v4i32_ty], [llvm_v4i32_ty], [llvm_v4i32_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
@ -85,146 +86,150 @@ class PowerPC_Vec_WWW_Intrinsic<string GCCIntSuffix>
let TargetPrefix = "ppc" in { // All intrinsics start with "llvm.ppc.". let TargetPrefix = "ppc" in { // All intrinsics start with "llvm.ppc.".
// Data Stream Control. // Data Stream Control.
def int_ppc_altivec_dss : GCCBuiltin<"__builtin_altivec_dss">, def int_ppc_altivec_dss : GCCBuiltin<"__builtin_altivec_dss">,
Intrinsic<[llvm_void_ty, llvm_i32_ty], [IntrWriteMem]>; Intrinsic<[llvm_void_ty], [llvm_i32_ty], [IntrWriteMem]>;
def int_ppc_altivec_dssall : GCCBuiltin<"__builtin_altivec_dssall">, def int_ppc_altivec_dssall : GCCBuiltin<"__builtin_altivec_dssall">,
Intrinsic<[llvm_void_ty], [IntrWriteMem]>; Intrinsic<[llvm_void_ty], [], [IntrWriteMem]>;
def int_ppc_altivec_dst : GCCBuiltin<"__builtin_altivec_dst">, def int_ppc_altivec_dst : GCCBuiltin<"__builtin_altivec_dst">,
Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_i32_ty, llvm_i32_ty], Intrinsic<[llvm_void_ty],
[llvm_ptr_ty, llvm_i32_ty, llvm_i32_ty],
[IntrWriteMem]>; [IntrWriteMem]>;
def int_ppc_altivec_dstt : GCCBuiltin<"__builtin_altivec_dstt">, def int_ppc_altivec_dstt : GCCBuiltin<"__builtin_altivec_dstt">,
Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_i32_ty, llvm_i32_ty], Intrinsic<[llvm_void_ty],
[llvm_ptr_ty, llvm_i32_ty, llvm_i32_ty],
[IntrWriteMem]>; [IntrWriteMem]>;
def int_ppc_altivec_dstst : GCCBuiltin<"__builtin_altivec_dstst">, def int_ppc_altivec_dstst : GCCBuiltin<"__builtin_altivec_dstst">,
Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_i32_ty, llvm_i32_ty], Intrinsic<[llvm_void_ty],
[llvm_ptr_ty, llvm_i32_ty, llvm_i32_ty],
[IntrWriteMem]>; [IntrWriteMem]>;
def int_ppc_altivec_dststt : GCCBuiltin<"__builtin_altivec_dststt">, def int_ppc_altivec_dststt : GCCBuiltin<"__builtin_altivec_dststt">,
Intrinsic<[llvm_void_ty, llvm_ptr_ty, llvm_i32_ty, llvm_i32_ty], Intrinsic<[llvm_void_ty],
[llvm_ptr_ty, llvm_i32_ty, llvm_i32_ty],
[IntrWriteMem]>; [IntrWriteMem]>;
// VSCR access. // VSCR access.
def int_ppc_altivec_mfvscr : GCCBuiltin<"__builtin_altivec_mfvscr">, def int_ppc_altivec_mfvscr : GCCBuiltin<"__builtin_altivec_mfvscr">,
Intrinsic<[llvm_v8i16_ty], [IntrReadMem]>; Intrinsic<[llvm_v8i16_ty], [], [IntrReadMem]>;
def int_ppc_altivec_mtvscr : GCCBuiltin<"__builtin_altivec_mtvscr">, def int_ppc_altivec_mtvscr : GCCBuiltin<"__builtin_altivec_mtvscr">,
Intrinsic<[llvm_void_ty, llvm_v4i32_ty], [IntrWriteMem]>; Intrinsic<[llvm_void_ty], [llvm_v4i32_ty], [IntrWriteMem]>;
// Loads. These don't map directly to GCC builtins because they represent the // Loads. These don't map directly to GCC builtins because they represent the
// source address with a single pointer. // source address with a single pointer.
def int_ppc_altivec_lvx : def int_ppc_altivec_lvx :
Intrinsic<[llvm_v4i32_ty, llvm_ptr_ty], [IntrReadMem]>; Intrinsic<[llvm_v4i32_ty], [llvm_ptr_ty], [IntrReadMem]>;
def int_ppc_altivec_lvxl : def int_ppc_altivec_lvxl :
Intrinsic<[llvm_v4i32_ty, llvm_ptr_ty], [IntrReadMem]>; Intrinsic<[llvm_v4i32_ty], [llvm_ptr_ty], [IntrReadMem]>;
def int_ppc_altivec_lvebx : def int_ppc_altivec_lvebx :
Intrinsic<[llvm_v16i8_ty, llvm_ptr_ty], [IntrReadMem]>; Intrinsic<[llvm_v16i8_ty], [llvm_ptr_ty], [IntrReadMem]>;
def int_ppc_altivec_lvehx : def int_ppc_altivec_lvehx :
Intrinsic<[llvm_v8i16_ty, llvm_ptr_ty], [IntrReadMem]>; Intrinsic<[llvm_v8i16_ty], [llvm_ptr_ty], [IntrReadMem]>;
def int_ppc_altivec_lvewx : def int_ppc_altivec_lvewx :
Intrinsic<[llvm_v4i32_ty, llvm_ptr_ty], [IntrReadMem]>; Intrinsic<[llvm_v4i32_ty], [llvm_ptr_ty], [IntrReadMem]>;
// Stores. These don't map directly to GCC builtins because they represent the // Stores. These don't map directly to GCC builtins because they represent the
// source address with a single pointer. // source address with a single pointer.
def int_ppc_altivec_stvx : def int_ppc_altivec_stvx :
Intrinsic<[llvm_void_ty, llvm_v4i32_ty, llvm_ptr_ty], Intrinsic<[llvm_void_ty], [llvm_v4i32_ty, llvm_ptr_ty],
[IntrWriteMem]>; [IntrWriteMem]>;
def int_ppc_altivec_stvxl : def int_ppc_altivec_stvxl :
Intrinsic<[llvm_void_ty, llvm_v4i32_ty, llvm_ptr_ty], Intrinsic<[llvm_void_ty], [llvm_v4i32_ty, llvm_ptr_ty],
[IntrWriteMem]>; [IntrWriteMem]>;
def int_ppc_altivec_stvebx : def int_ppc_altivec_stvebx :
Intrinsic<[llvm_void_ty, llvm_v16i8_ty, llvm_ptr_ty], Intrinsic<[llvm_void_ty], [llvm_v16i8_ty, llvm_ptr_ty],
[IntrWriteMem]>; [IntrWriteMem]>;
def int_ppc_altivec_stvehx : def int_ppc_altivec_stvehx :
Intrinsic<[llvm_void_ty, llvm_v8i16_ty, llvm_ptr_ty], Intrinsic<[llvm_void_ty], [llvm_v8i16_ty, llvm_ptr_ty],
[IntrWriteMem]>; [IntrWriteMem]>;
def int_ppc_altivec_stvewx : def int_ppc_altivec_stvewx :
Intrinsic<[llvm_void_ty, llvm_v4i32_ty, llvm_ptr_ty], Intrinsic<[llvm_void_ty], [llvm_v4i32_ty, llvm_ptr_ty],
[IntrWriteMem]>; [IntrWriteMem]>;
// Comparisons setting a vector. // Comparisons setting a vector.
def int_ppc_altivec_vcmpbfp : GCCBuiltin<"__builtin_altivec_vcmpbfp">, def int_ppc_altivec_vcmpbfp : GCCBuiltin<"__builtin_altivec_vcmpbfp">,
Intrinsic<[llvm_v4i32_ty, llvm_v4f32_ty, llvm_v4f32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4f32_ty, llvm_v4f32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpeqfp : GCCBuiltin<"__builtin_altivec_vcmpeqfp">, def int_ppc_altivec_vcmpeqfp : GCCBuiltin<"__builtin_altivec_vcmpeqfp">,
Intrinsic<[llvm_v4i32_ty, llvm_v4f32_ty, llvm_v4f32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4f32_ty, llvm_v4f32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgefp : GCCBuiltin<"__builtin_altivec_vcmpgefp">, def int_ppc_altivec_vcmpgefp : GCCBuiltin<"__builtin_altivec_vcmpgefp">,
Intrinsic<[llvm_v4i32_ty, llvm_v4f32_ty, llvm_v4f32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4f32_ty, llvm_v4f32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtfp : GCCBuiltin<"__builtin_altivec_vcmpgtfp">, def int_ppc_altivec_vcmpgtfp : GCCBuiltin<"__builtin_altivec_vcmpgtfp">,
Intrinsic<[llvm_v4i32_ty, llvm_v4f32_ty, llvm_v4f32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4f32_ty, llvm_v4f32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpequw : GCCBuiltin<"__builtin_altivec_vcmpequw">, def int_ppc_altivec_vcmpequw : GCCBuiltin<"__builtin_altivec_vcmpequw">,
Intrinsic<[llvm_v4i32_ty, llvm_v4i32_ty, llvm_v4i32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4i32_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtsw : GCCBuiltin<"__builtin_altivec_vcmpgtsw">, def int_ppc_altivec_vcmpgtsw : GCCBuiltin<"__builtin_altivec_vcmpgtsw">,
Intrinsic<[llvm_v4i32_ty, llvm_v4i32_ty, llvm_v4i32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4i32_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtuw : GCCBuiltin<"__builtin_altivec_vcmpgtuw">, def int_ppc_altivec_vcmpgtuw : GCCBuiltin<"__builtin_altivec_vcmpgtuw">,
Intrinsic<[llvm_v4i32_ty, llvm_v4i32_ty, llvm_v4i32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4i32_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpequh : GCCBuiltin<"__builtin_altivec_vcmpequh">, def int_ppc_altivec_vcmpequh : GCCBuiltin<"__builtin_altivec_vcmpequh">,
Intrinsic<[llvm_v8i16_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtsh : GCCBuiltin<"__builtin_altivec_vcmpgtsh">, def int_ppc_altivec_vcmpgtsh : GCCBuiltin<"__builtin_altivec_vcmpgtsh">,
Intrinsic<[llvm_v8i16_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtuh : GCCBuiltin<"__builtin_altivec_vcmpgtuh">, def int_ppc_altivec_vcmpgtuh : GCCBuiltin<"__builtin_altivec_vcmpgtuh">,
Intrinsic<[llvm_v8i16_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpequb : GCCBuiltin<"__builtin_altivec_vcmpequb">, def int_ppc_altivec_vcmpequb : GCCBuiltin<"__builtin_altivec_vcmpequb">,
Intrinsic<[llvm_v16i8_ty, llvm_v16i8_ty, llvm_v16i8_ty], Intrinsic<[llvm_v16i8_ty], [llvm_v16i8_ty, llvm_v16i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtsb : GCCBuiltin<"__builtin_altivec_vcmpgtsb">, def int_ppc_altivec_vcmpgtsb : GCCBuiltin<"__builtin_altivec_vcmpgtsb">,
Intrinsic<[llvm_v16i8_ty, llvm_v16i8_ty, llvm_v16i8_ty], Intrinsic<[llvm_v16i8_ty], [llvm_v16i8_ty, llvm_v16i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtub : GCCBuiltin<"__builtin_altivec_vcmpgtub">, def int_ppc_altivec_vcmpgtub : GCCBuiltin<"__builtin_altivec_vcmpgtub">,
Intrinsic<[llvm_v16i8_ty, llvm_v16i8_ty, llvm_v16i8_ty], Intrinsic<[llvm_v16i8_ty], [llvm_v16i8_ty, llvm_v16i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
// Predicate Comparisons. The first operand specifies interpretation of CR6. // Predicate Comparisons. The first operand specifies interpretation of CR6.
def int_ppc_altivec_vcmpbfp_p : GCCBuiltin<"__builtin_altivec_vcmpbfp_p">, def int_ppc_altivec_vcmpbfp_p : GCCBuiltin<"__builtin_altivec_vcmpbfp_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v4f32_ty,llvm_v4f32_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v4f32_ty,llvm_v4f32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpeqfp_p : GCCBuiltin<"__builtin_altivec_vcmpeqfp_p">, def int_ppc_altivec_vcmpeqfp_p : GCCBuiltin<"__builtin_altivec_vcmpeqfp_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v4f32_ty,llvm_v4f32_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v4f32_ty,llvm_v4f32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgefp_p : GCCBuiltin<"__builtin_altivec_vcmpgefp_p">, def int_ppc_altivec_vcmpgefp_p : GCCBuiltin<"__builtin_altivec_vcmpgefp_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v4f32_ty,llvm_v4f32_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v4f32_ty,llvm_v4f32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtfp_p : GCCBuiltin<"__builtin_altivec_vcmpgtfp_p">, def int_ppc_altivec_vcmpgtfp_p : GCCBuiltin<"__builtin_altivec_vcmpgtfp_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v4f32_ty,llvm_v4f32_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v4f32_ty,llvm_v4f32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpequw_p : GCCBuiltin<"__builtin_altivec_vcmpequw_p">, def int_ppc_altivec_vcmpequw_p : GCCBuiltin<"__builtin_altivec_vcmpequw_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v4i32_ty,llvm_v4i32_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v4i32_ty,llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtsw_p : GCCBuiltin<"__builtin_altivec_vcmpgtsw_p">, def int_ppc_altivec_vcmpgtsw_p : GCCBuiltin<"__builtin_altivec_vcmpgtsw_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v4i32_ty,llvm_v4i32_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v4i32_ty,llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtuw_p : GCCBuiltin<"__builtin_altivec_vcmpgtuw_p">, def int_ppc_altivec_vcmpgtuw_p : GCCBuiltin<"__builtin_altivec_vcmpgtuw_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v4i32_ty,llvm_v4i32_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v4i32_ty,llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpequh_p : GCCBuiltin<"__builtin_altivec_vcmpequh_p">, def int_ppc_altivec_vcmpequh_p : GCCBuiltin<"__builtin_altivec_vcmpequh_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v8i16_ty,llvm_v8i16_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v8i16_ty,llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtsh_p : GCCBuiltin<"__builtin_altivec_vcmpgtsh_p">, def int_ppc_altivec_vcmpgtsh_p : GCCBuiltin<"__builtin_altivec_vcmpgtsh_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v8i16_ty,llvm_v8i16_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v8i16_ty,llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtuh_p : GCCBuiltin<"__builtin_altivec_vcmpgtuh_p">, def int_ppc_altivec_vcmpgtuh_p : GCCBuiltin<"__builtin_altivec_vcmpgtuh_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v8i16_ty,llvm_v8i16_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v8i16_ty,llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpequb_p : GCCBuiltin<"__builtin_altivec_vcmpequb_p">, def int_ppc_altivec_vcmpequb_p : GCCBuiltin<"__builtin_altivec_vcmpequb_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v16i8_ty,llvm_v16i8_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v16i8_ty,llvm_v16i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtsb_p : GCCBuiltin<"__builtin_altivec_vcmpgtsb_p">, def int_ppc_altivec_vcmpgtsb_p : GCCBuiltin<"__builtin_altivec_vcmpgtsb_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v16i8_ty,llvm_v16i8_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v16i8_ty,llvm_v16i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcmpgtub_p : GCCBuiltin<"__builtin_altivec_vcmpgtub_p">, def int_ppc_altivec_vcmpgtub_p : GCCBuiltin<"__builtin_altivec_vcmpgtub_p">,
Intrinsic<[llvm_i32_ty, llvm_i32_ty, llvm_v16i8_ty,llvm_v16i8_ty], Intrinsic<[llvm_i32_ty],[llvm_i32_ty,llvm_v16i8_ty,llvm_v16i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
} }
@ -275,150 +280,150 @@ def int_ppc_altivec_vsubcuw : PowerPC_Vec_WWW_Intrinsic<"vsubcuw">;
let TargetPrefix = "ppc" in { // All PPC intrinsics start with "llvm.ppc.". let TargetPrefix = "ppc" in { // All PPC intrinsics start with "llvm.ppc.".
// Saturating multiply-adds. // Saturating multiply-adds.
def int_ppc_altivec_vmhaddshs : GCCBuiltin<"__builtin_altivec_vmhaddshs">, def int_ppc_altivec_vmhaddshs : GCCBuiltin<"__builtin_altivec_vmhaddshs">,
Intrinsic<[llvm_v8i16_ty, llvm_v8i16_ty, Intrinsic<[llvm_v8i16_ty], [llvm_v8i16_ty,
llvm_v8i16_ty, llvm_v8i16_ty], [IntrNoMem]>; llvm_v8i16_ty, llvm_v8i16_ty], [IntrNoMem]>;
def int_ppc_altivec_vmhraddshs : GCCBuiltin<"__builtin_altivec_vmhraddshs">, def int_ppc_altivec_vmhraddshs : GCCBuiltin<"__builtin_altivec_vmhraddshs">,
Intrinsic<[llvm_v8i16_ty, llvm_v8i16_ty, Intrinsic<[llvm_v8i16_ty], [llvm_v8i16_ty,
llvm_v8i16_ty, llvm_v8i16_ty], [IntrNoMem]>; llvm_v8i16_ty, llvm_v8i16_ty], [IntrNoMem]>;
def int_ppc_altivec_vmaddfp : GCCBuiltin<"__builtin_altivec_vmaddfp">, def int_ppc_altivec_vmaddfp : GCCBuiltin<"__builtin_altivec_vmaddfp">,
Intrinsic<[llvm_v4f32_ty, llvm_v4f32_ty, Intrinsic<[llvm_v4f32_ty], [llvm_v4f32_ty,
llvm_v4f32_ty, llvm_v4f32_ty], [IntrNoMem]>; llvm_v4f32_ty, llvm_v4f32_ty], [IntrNoMem]>;
def int_ppc_altivec_vnmsubfp : GCCBuiltin<"__builtin_altivec_vnmsubfp">, def int_ppc_altivec_vnmsubfp : GCCBuiltin<"__builtin_altivec_vnmsubfp">,
Intrinsic<[llvm_v4f32_ty, llvm_v4f32_ty, Intrinsic<[llvm_v4f32_ty], [llvm_v4f32_ty,
llvm_v4f32_ty, llvm_v4f32_ty], [IntrNoMem]>; llvm_v4f32_ty, llvm_v4f32_ty], [IntrNoMem]>;
// Vector Multiply Sum Intructions. // Vector Multiply Sum Intructions.
def int_ppc_altivec_vmsummbm : GCCBuiltin<"__builtin_altivec_vmsummbm">, def int_ppc_altivec_vmsummbm : GCCBuiltin<"__builtin_altivec_vmsummbm">,
Intrinsic<[llvm_v4i32_ty, llvm_v16i8_ty, llvm_v16i8_ty, Intrinsic<[llvm_v4i32_ty], [llvm_v16i8_ty, llvm_v16i8_ty,
llvm_v4i32_ty], [IntrNoMem]>; llvm_v4i32_ty], [IntrNoMem]>;
def int_ppc_altivec_vmsumshm : GCCBuiltin<"__builtin_altivec_vmsumshm">, def int_ppc_altivec_vmsumshm : GCCBuiltin<"__builtin_altivec_vmsumshm">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty, Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty,
llvm_v4i32_ty], [IntrNoMem]>; llvm_v4i32_ty], [IntrNoMem]>;
def int_ppc_altivec_vmsumshs : GCCBuiltin<"__builtin_altivec_vmsumshs">, def int_ppc_altivec_vmsumshs : GCCBuiltin<"__builtin_altivec_vmsumshs">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty, Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty,
llvm_v4i32_ty], [IntrNoMem]>; llvm_v4i32_ty], [IntrNoMem]>;
def int_ppc_altivec_vmsumubm : GCCBuiltin<"__builtin_altivec_vmsumubm">, def int_ppc_altivec_vmsumubm : GCCBuiltin<"__builtin_altivec_vmsumubm">,
Intrinsic<[llvm_v4i32_ty, llvm_v16i8_ty, llvm_v16i8_ty, Intrinsic<[llvm_v4i32_ty], [llvm_v16i8_ty, llvm_v16i8_ty,
llvm_v4i32_ty], [IntrNoMem]>; llvm_v4i32_ty], [IntrNoMem]>;
def int_ppc_altivec_vmsumuhm : GCCBuiltin<"__builtin_altivec_vmsumuhm">, def int_ppc_altivec_vmsumuhm : GCCBuiltin<"__builtin_altivec_vmsumuhm">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty, Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty,
llvm_v4i32_ty], [IntrNoMem]>; llvm_v4i32_ty], [IntrNoMem]>;
def int_ppc_altivec_vmsumuhs : GCCBuiltin<"__builtin_altivec_vmsumuhs">, def int_ppc_altivec_vmsumuhs : GCCBuiltin<"__builtin_altivec_vmsumuhs">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty, Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty,
llvm_v4i32_ty], [IntrNoMem]>; llvm_v4i32_ty], [IntrNoMem]>;
// Vector Multiply Intructions. // Vector Multiply Intructions.
def int_ppc_altivec_vmulesb : GCCBuiltin<"__builtin_altivec_vmulesb">, def int_ppc_altivec_vmulesb : GCCBuiltin<"__builtin_altivec_vmulesb">,
Intrinsic<[llvm_v8i16_ty, llvm_v16i8_ty, llvm_v16i8_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v16i8_ty, llvm_v16i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vmulesh : GCCBuiltin<"__builtin_altivec_vmulesh">, def int_ppc_altivec_vmulesh : GCCBuiltin<"__builtin_altivec_vmulesh">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vmuleub : GCCBuiltin<"__builtin_altivec_vmuleub">, def int_ppc_altivec_vmuleub : GCCBuiltin<"__builtin_altivec_vmuleub">,
Intrinsic<[llvm_v8i16_ty, llvm_v16i8_ty, llvm_v16i8_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v16i8_ty, llvm_v16i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vmuleuh : GCCBuiltin<"__builtin_altivec_vmuleuh">, def int_ppc_altivec_vmuleuh : GCCBuiltin<"__builtin_altivec_vmuleuh">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vmulosb : GCCBuiltin<"__builtin_altivec_vmulosb">, def int_ppc_altivec_vmulosb : GCCBuiltin<"__builtin_altivec_vmulosb">,
Intrinsic<[llvm_v8i16_ty, llvm_v16i8_ty, llvm_v16i8_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v16i8_ty, llvm_v16i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vmulosh : GCCBuiltin<"__builtin_altivec_vmulosh">, def int_ppc_altivec_vmulosh : GCCBuiltin<"__builtin_altivec_vmulosh">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vmuloub : GCCBuiltin<"__builtin_altivec_vmuloub">, def int_ppc_altivec_vmuloub : GCCBuiltin<"__builtin_altivec_vmuloub">,
Intrinsic<[llvm_v8i16_ty, llvm_v16i8_ty, llvm_v16i8_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v16i8_ty, llvm_v16i8_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vmulouh : GCCBuiltin<"__builtin_altivec_vmulouh">, def int_ppc_altivec_vmulouh : GCCBuiltin<"__builtin_altivec_vmulouh">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
// Vector Sum Intructions. // Vector Sum Intructions.
def int_ppc_altivec_vsumsws : GCCBuiltin<"__builtin_altivec_vsumsws">, def int_ppc_altivec_vsumsws : GCCBuiltin<"__builtin_altivec_vsumsws">,
Intrinsic<[llvm_v4i32_ty, llvm_v4i32_ty, llvm_v4i32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4i32_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vsum2sws : GCCBuiltin<"__builtin_altivec_vsum2sws">, def int_ppc_altivec_vsum2sws : GCCBuiltin<"__builtin_altivec_vsum2sws">,
Intrinsic<[llvm_v4i32_ty, llvm_v4i32_ty, llvm_v4i32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4i32_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vsum4sbs : GCCBuiltin<"__builtin_altivec_vsum4sbs">, def int_ppc_altivec_vsum4sbs : GCCBuiltin<"__builtin_altivec_vsum4sbs">,
Intrinsic<[llvm_v4i32_ty, llvm_v16i8_ty, llvm_v4i32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v16i8_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vsum4shs : GCCBuiltin<"__builtin_altivec_vsum4shs">, def int_ppc_altivec_vsum4shs : GCCBuiltin<"__builtin_altivec_vsum4shs">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty, llvm_v4i32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vsum4ubs : GCCBuiltin<"__builtin_altivec_vsum4ubs">, def int_ppc_altivec_vsum4ubs : GCCBuiltin<"__builtin_altivec_vsum4ubs">,
Intrinsic<[llvm_v4i32_ty, llvm_v16i8_ty, llvm_v4i32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v16i8_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
// Other multiplies. // Other multiplies.
def int_ppc_altivec_vmladduhm : GCCBuiltin<"__builtin_altivec_vmladduhm">, def int_ppc_altivec_vmladduhm : GCCBuiltin<"__builtin_altivec_vmladduhm">,
Intrinsic<[llvm_v8i16_ty, llvm_v8i16_ty, llvm_v8i16_ty, Intrinsic<[llvm_v8i16_ty], [llvm_v8i16_ty, llvm_v8i16_ty,
llvm_v8i16_ty], [IntrNoMem]>; llvm_v8i16_ty], [IntrNoMem]>;
// Packs. // Packs.
def int_ppc_altivec_vpkpx : GCCBuiltin<"__builtin_altivec_vpkpx">, def int_ppc_altivec_vpkpx : GCCBuiltin<"__builtin_altivec_vpkpx">,
Intrinsic<[llvm_v8i16_ty, llvm_v4i32_ty, llvm_v4i32_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v4i32_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vpkshss : GCCBuiltin<"__builtin_altivec_vpkshss">, def int_ppc_altivec_vpkshss : GCCBuiltin<"__builtin_altivec_vpkshss">,
Intrinsic<[llvm_v16i8_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v16i8_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vpkshus : GCCBuiltin<"__builtin_altivec_vpkshus">, def int_ppc_altivec_vpkshus : GCCBuiltin<"__builtin_altivec_vpkshus">,
Intrinsic<[llvm_v16i8_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v16i8_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vpkswss : GCCBuiltin<"__builtin_altivec_vpkswss">, def int_ppc_altivec_vpkswss : GCCBuiltin<"__builtin_altivec_vpkswss">,
Intrinsic<[llvm_v16i8_ty, llvm_v4i32_ty, llvm_v4i32_ty], Intrinsic<[llvm_v16i8_ty], [llvm_v4i32_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vpkswus : GCCBuiltin<"__builtin_altivec_vpkswus">, def int_ppc_altivec_vpkswus : GCCBuiltin<"__builtin_altivec_vpkswus">,
Intrinsic<[llvm_v8i16_ty, llvm_v4i32_ty, llvm_v4i32_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v4i32_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
// vpkuhum is lowered to a shuffle. // vpkuhum is lowered to a shuffle.
def int_ppc_altivec_vpkuhus : GCCBuiltin<"__builtin_altivec_vpkuhus">, def int_ppc_altivec_vpkuhus : GCCBuiltin<"__builtin_altivec_vpkuhus">,
Intrinsic<[llvm_v16i8_ty, llvm_v8i16_ty, llvm_v8i16_ty], Intrinsic<[llvm_v16i8_ty], [llvm_v8i16_ty, llvm_v8i16_ty],
[IntrNoMem]>; [IntrNoMem]>;
// vpkuwum is lowered to a shuffle. // vpkuwum is lowered to a shuffle.
def int_ppc_altivec_vpkuwus : GCCBuiltin<"__builtin_altivec_vpkuwus">, def int_ppc_altivec_vpkuwus : GCCBuiltin<"__builtin_altivec_vpkuwus">,
Intrinsic<[llvm_v8i16_ty, llvm_v4i32_ty, llvm_v4i32_ty], Intrinsic<[llvm_v8i16_ty], [llvm_v4i32_ty, llvm_v4i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
// Unpacks. // Unpacks.
def int_ppc_altivec_vupkhpx : GCCBuiltin<"__builtin_altivec_vupkhpx">, def int_ppc_altivec_vupkhpx : GCCBuiltin<"__builtin_altivec_vupkhpx">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty], [IntrNoMem]>; Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty], [IntrNoMem]>;
def int_ppc_altivec_vupkhsb : GCCBuiltin<"__builtin_altivec_vupkhsb">, def int_ppc_altivec_vupkhsb : GCCBuiltin<"__builtin_altivec_vupkhsb">,
Intrinsic<[llvm_v8i16_ty, llvm_v16i8_ty], [IntrNoMem]>; Intrinsic<[llvm_v8i16_ty], [llvm_v16i8_ty], [IntrNoMem]>;
def int_ppc_altivec_vupkhsh : GCCBuiltin<"__builtin_altivec_vupkhsh">, def int_ppc_altivec_vupkhsh : GCCBuiltin<"__builtin_altivec_vupkhsh">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty], [IntrNoMem]>; Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty], [IntrNoMem]>;
def int_ppc_altivec_vupklpx : GCCBuiltin<"__builtin_altivec_vupklpx">, def int_ppc_altivec_vupklpx : GCCBuiltin<"__builtin_altivec_vupklpx">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty], [IntrNoMem]>; Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty], [IntrNoMem]>;
def int_ppc_altivec_vupklsb : GCCBuiltin<"__builtin_altivec_vupklsb">, def int_ppc_altivec_vupklsb : GCCBuiltin<"__builtin_altivec_vupklsb">,
Intrinsic<[llvm_v8i16_ty, llvm_v16i8_ty], [IntrNoMem]>; Intrinsic<[llvm_v8i16_ty], [llvm_v16i8_ty], [IntrNoMem]>;
def int_ppc_altivec_vupklsh : GCCBuiltin<"__builtin_altivec_vupklsh">, def int_ppc_altivec_vupklsh : GCCBuiltin<"__builtin_altivec_vupklsh">,
Intrinsic<[llvm_v4i32_ty, llvm_v8i16_ty], [IntrNoMem]>; Intrinsic<[llvm_v4i32_ty], [llvm_v8i16_ty], [IntrNoMem]>;
// FP <-> integer conversion. // FP <-> integer conversion.
def int_ppc_altivec_vcfsx : GCCBuiltin<"__builtin_altivec_vcfsx">, def int_ppc_altivec_vcfsx : GCCBuiltin<"__builtin_altivec_vcfsx">,
Intrinsic<[llvm_v4f32_ty, llvm_v4i32_ty, llvm_i32_ty], Intrinsic<[llvm_v4f32_ty], [llvm_v4i32_ty, llvm_i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vcfux : GCCBuiltin<"__builtin_altivec_vcfux">, def int_ppc_altivec_vcfux : GCCBuiltin<"__builtin_altivec_vcfux">,
Intrinsic<[llvm_v4f32_ty, llvm_v4i32_ty, llvm_i32_ty], Intrinsic<[llvm_v4f32_ty], [llvm_v4i32_ty, llvm_i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vctsxs : GCCBuiltin<"__builtin_altivec_vctsxs">, def int_ppc_altivec_vctsxs : GCCBuiltin<"__builtin_altivec_vctsxs">,
Intrinsic<[llvm_v4i32_ty, llvm_v4f32_ty, llvm_i32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4f32_ty, llvm_i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vctuxs : GCCBuiltin<"__builtin_altivec_vctuxs">, def int_ppc_altivec_vctuxs : GCCBuiltin<"__builtin_altivec_vctuxs">,
Intrinsic<[llvm_v4i32_ty, llvm_v4f32_ty, llvm_i32_ty], Intrinsic<[llvm_v4i32_ty], [llvm_v4f32_ty, llvm_i32_ty],
[IntrNoMem]>; [IntrNoMem]>;
def int_ppc_altivec_vrfim : GCCBuiltin<"__builtin_altivec_vrfim">, def int_ppc_altivec_vrfim : GCCBuiltin<"__builtin_altivec_vrfim">,
Intrinsic<[llvm_v4f32_ty, llvm_v4f32_ty], [IntrNoMem]>; Intrinsic<[llvm_v4f32_ty], [llvm_v4f32_ty], [IntrNoMem]>;
def int_ppc_altivec_vrfin : GCCBuiltin<"__builtin_altivec_vrfin">, def int_ppc_altivec_vrfin : GCCBuiltin<"__builtin_altivec_vrfin">,
Intrinsic<[llvm_v4f32_ty, llvm_v4f32_ty], [IntrNoMem]>; Intrinsic<[llvm_v4f32_ty], [llvm_v4f32_ty], [IntrNoMem]>;
def int_ppc_altivec_vrfip : GCCBuiltin<"__builtin_altivec_vrfip">, def int_ppc_altivec_vrfip : GCCBuiltin<"__builtin_altivec_vrfip">,
Intrinsic<[llvm_v4f32_ty, llvm_v4f32_ty], [IntrNoMem]>; Intrinsic<[llvm_v4f32_ty], [llvm_v4f32_ty], [IntrNoMem]>;
def int_ppc_altivec_vrfiz : GCCBuiltin<"__builtin_altivec_vrfiz">, def int_ppc_altivec_vrfiz : GCCBuiltin<"__builtin_altivec_vrfiz">,
Intrinsic<[llvm_v4f32_ty, llvm_v4f32_ty], [IntrNoMem]>; Intrinsic<[llvm_v4f32_ty], [llvm_v4f32_ty], [IntrNoMem]>;
} }
def int_ppc_altivec_vsl : PowerPC_Vec_WWW_Intrinsic<"vsl">; def int_ppc_altivec_vsl : PowerPC_Vec_WWW_Intrinsic<"vsl">;
@ -447,15 +452,15 @@ def int_ppc_altivec_vrlw : PowerPC_Vec_WWW_Intrinsic<"vrlw">;
let TargetPrefix = "ppc" in { // All PPC intrinsics start with "llvm.ppc.". let TargetPrefix = "ppc" in { // All PPC intrinsics start with "llvm.ppc.".
// Miscellaneous. // Miscellaneous.
def int_ppc_altivec_lvsl : def int_ppc_altivec_lvsl :
Intrinsic<[llvm_v16i8_ty, llvm_ptr_ty], [IntrNoMem]>; Intrinsic<[llvm_v16i8_ty], [llvm_ptr_ty], [IntrNoMem]>;
def int_ppc_altivec_lvsr : def int_ppc_altivec_lvsr :
Intrinsic<[llvm_v16i8_ty, llvm_ptr_ty], [IntrNoMem]>; Intrinsic<[llvm_v16i8_ty], [llvm_ptr_ty], [IntrNoMem]>;
def int_ppc_altivec_vperm : GCCBuiltin<"__builtin_altivec_vperm_4si">, def int_ppc_altivec_vperm : GCCBuiltin<"__builtin_altivec_vperm_4si">,
Intrinsic<[llvm_v4i32_ty, llvm_v4i32_ty, Intrinsic<[llvm_v4i32_ty], [llvm_v4i32_ty,
llvm_v4i32_ty, llvm_v16i8_ty], [IntrNoMem]>; llvm_v4i32_ty, llvm_v16i8_ty], [IntrNoMem]>;
def int_ppc_altivec_vsel : GCCBuiltin<"__builtin_altivec_vsel_4si">, def int_ppc_altivec_vsel : GCCBuiltin<"__builtin_altivec_vsel_4si">,
Intrinsic<[llvm_v4i32_ty, llvm_v4i32_ty, Intrinsic<[llvm_v4i32_ty], [llvm_v4i32_ty,
llvm_v4i32_ty, llvm_v4i32_ty], [IntrNoMem]>; llvm_v4i32_ty, llvm_v4i32_ty], [IntrNoMem]>;
} }

File diff suppressed because it is too large Load Diff

View File

@ -269,7 +269,7 @@ namespace {
bool PerformTypeCheck(Intrinsic::ID ID, Function *F, const Type *Ty, bool PerformTypeCheck(Intrinsic::ID ID, Function *F, const Type *Ty,
int VT, unsigned ArgNo, std::string &Suffix); int VT, unsigned ArgNo, std::string &Suffix);
void VerifyIntrinsicPrototype(Intrinsic::ID ID, Function *F, void VerifyIntrinsicPrototype(Intrinsic::ID ID, Function *F,
unsigned Count, ...); unsigned RetNum, unsigned ParamNum, ...);
void VerifyAttrs(Attributes Attrs, const Type *Ty, void VerifyAttrs(Attributes Attrs, const Type *Ty,
bool isReturnValue, const Value *V); bool isReturnValue, const Value *V);
void VerifyFunctionAttrs(const FunctionType *FT, const AttrListPtr &Attrs, void VerifyFunctionAttrs(const FunctionType *FT, const AttrListPtr &Attrs,
@ -1507,11 +1507,11 @@ bool Verifier::PerformTypeCheck(Intrinsic::ID ID, Function *F, const Type *Ty,
/// VerifyIntrinsicPrototype - TableGen emits calls to this function into /// VerifyIntrinsicPrototype - TableGen emits calls to this function into
/// Intrinsics.gen. This implements a little state machine that verifies the /// Intrinsics.gen. This implements a little state machine that verifies the
/// prototype of intrinsics. /// prototype of intrinsics.
void Verifier::VerifyIntrinsicPrototype(Intrinsic::ID ID, void Verifier::VerifyIntrinsicPrototype(Intrinsic::ID ID, Function *F,
Function *F, unsigned RetNum,
unsigned Count, ...) { unsigned ParamNum, ...) {
va_list VA; va_list VA;
va_start(VA, Count); va_start(VA, ParamNum);
const FunctionType *FTy = F->getFunctionType(); const FunctionType *FTy = F->getFunctionType();
// For overloaded intrinsics, the Suffix of the function name must match the // For overloaded intrinsics, the Suffix of the function name must match the
@ -1519,13 +1519,31 @@ void Verifier::VerifyIntrinsicPrototype(Intrinsic::ID ID,
// suffix, to be checked at the end. // suffix, to be checked at the end.
std::string Suffix; std::string Suffix;
if (FTy->getNumParams() + FTy->isVarArg() != Count - 1) { if (FTy->getNumParams() + FTy->isVarArg() != ParamNum) {
CheckFailed("Intrinsic prototype has incorrect number of arguments!", F); CheckFailed("Intrinsic prototype has incorrect number of arguments!", F);
return; return;
} }
// Note that "arg#0" is the return type. const Type *Ty = FTy->getReturnType();
for (unsigned ArgNo = 0; ArgNo < Count; ++ArgNo) { const StructType *ST = dyn_cast<StructType>(Ty);
// Verify the return types.
if (ST && ST->getNumElements() != RetNum) {
CheckFailed("Intrinsic prototype has incorrect number of return types!", F);
return;
}
for (unsigned ArgNo = 0; ArgNo < RetNum; ++ArgNo) {
int VT = va_arg(VA, int); // An MVT::SimpleValueType when non-negative.
if (ST) Ty = ST->getElementType(ArgNo);
if (!PerformTypeCheck(ID, F, Ty, VT, ArgNo, Suffix))
break;
}
// Verify the parameter types.
for (unsigned ArgNo = 0; ArgNo < ParamNum; ++ArgNo) {
int VT = va_arg(VA, int); // An MVT::SimpleValueType when non-negative. int VT = va_arg(VA, int); // An MVT::SimpleValueType when non-negative.
if (VT == MVT::isVoid && ArgNo > 0) { if (VT == MVT::isVoid && ArgNo > 0) {
@ -1534,10 +1552,7 @@ void Verifier::VerifyIntrinsicPrototype(Intrinsic::ID ID,
break; break;
} }
const Type *Ty = (ArgNo == 0) ? if (!PerformTypeCheck(ID, F, FTy->getParamType(ArgNo), VT, ArgNo, Suffix))
FTy->getReturnType() : FTy->getParamType(ArgNo - 1);
if (!PerformTypeCheck(ID, F, Ty, VT, ArgNo, Suffix))
break; break;
} }

View File

@ -471,7 +471,8 @@ bool TreePatternNode::UpdateNodeType(const std::vector<unsigned char> &ExtVTs,
} }
if (getExtTypeNum(0) == MVT::iPTR || getExtTypeNum(0) == MVT::iPTRAny) { if (getExtTypeNum(0) == MVT::iPTR || getExtTypeNum(0) == MVT::iPTRAny) {
if (ExtVTs[0] == MVT::iPTR || ExtVTs[0] == MVT::iPTRAny || ExtVTs[0] == EMVT::isInt) if (ExtVTs[0] == MVT::iPTR || ExtVTs[0] == MVT::iPTRAny ||
ExtVTs[0] == EMVT::isInt)
return false; return false;
if (EMVT::isExtIntegerInVTs(ExtVTs)) { if (EMVT::isExtIntegerInVTs(ExtVTs)) {
std::vector<unsigned char> FVTs = FilterEVTs(ExtVTs, isInteger); std::vector<unsigned char> FVTs = FilterEVTs(ExtVTs, isInteger);
@ -885,18 +886,22 @@ bool TreePatternNode::ApplyTypeConstraints(TreePattern &TP, bool NotRegisters) {
bool MadeChange = false; bool MadeChange = false;
// Apply the result type to the node. // Apply the result type to the node.
MadeChange = UpdateNodeType(Int->ArgVTs[0], TP); unsigned NumRetVTs = Int->IS.RetVTs.size();
unsigned NumParamVTs = Int->IS.ParamVTs.size();
if (getNumChildren() != Int->ArgVTs.size()) for (unsigned i = 0, e = NumRetVTs; i != e; ++i)
MadeChange |= UpdateNodeType(Int->IS.RetVTs[i], TP);
if (getNumChildren() != NumParamVTs + NumRetVTs)
TP.error("Intrinsic '" + Int->Name + "' expects " + TP.error("Intrinsic '" + Int->Name + "' expects " +
utostr(Int->ArgVTs.size()-1) + " operands, not " + utostr(NumParamVTs + NumRetVTs - 1) + " operands, not " +
utostr(getNumChildren()-1) + " operands!"); utostr(getNumChildren() - 1) + " operands!");
// Apply type info to the intrinsic ID. // Apply type info to the intrinsic ID.
MadeChange |= getChild(0)->UpdateNodeType(MVT::iPTR, TP); MadeChange |= getChild(0)->UpdateNodeType(MVT::iPTR, TP);
for (unsigned i = 1, e = getNumChildren(); i != e; ++i) { for (unsigned i = NumRetVTs, e = getNumChildren(); i != e; ++i) {
MVT::SimpleValueType OpVT = Int->ArgVTs[i]; MVT::SimpleValueType OpVT = Int->IS.ParamVTs[i - NumRetVTs];
MadeChange |= getChild(i)->UpdateNodeType(OpVT, TP); MadeChange |= getChild(i)->UpdateNodeType(OpVT, TP);
MadeChange |= getChild(i)->ApplyTypeConstraints(TP, NotRegisters); MadeChange |= getChild(i)->ApplyTypeConstraints(TP, NotRegisters);
} }
@ -1232,7 +1237,7 @@ TreePatternNode *TreePattern::ParseTreePattern(DagInit *Dag) {
// If this intrinsic returns void, it must have side-effects and thus a // If this intrinsic returns void, it must have side-effects and thus a
// chain. // chain.
if (Int.ArgVTs[0] == MVT::isVoid) { if (Int.IS.RetVTs[0] == MVT::isVoid) {
Operator = getDAGPatterns().get_intrinsic_void_sdnode(); Operator = getDAGPatterns().get_intrinsic_void_sdnode();
} else if (Int.ModRef != CodeGenIntrinsic::NoMem) { } else if (Int.ModRef != CodeGenIntrinsic::NoMem) {
// Has side-effects, requires chain. // Has side-effects, requires chain.

View File

@ -30,15 +30,33 @@ namespace llvm {
std::string GCCBuiltinName;// Name of the corresponding GCC builtin, or "". std::string GCCBuiltinName;// Name of the corresponding GCC builtin, or "".
std::string TargetPrefix; // Target prefix, e.g. "ppc" for t-s intrinsics. std::string TargetPrefix; // Target prefix, e.g. "ppc" for t-s intrinsics.
/// ArgVTs - The MVT::SimpleValueType for each argument type. Note that /// IntrinsicSignature - This structure holds the return values and
/// this list is only populated when in the context of a target .td file. /// parameter values of an intrinsic. If the number of return values is > 1,
/// When building Intrinsics.td, this isn't available, because we don't know /// then the intrinsic implicitly returns a first-class aggregate. The
/// the target pointer size. /// numbering of the types starts at 0 with the first return value and
std::vector<MVT::SimpleValueType> ArgVTs; /// continues from there throug the parameter list. This is useful for
/// "matching" types.
struct IntrinsicSignature {
/// RetVTs - The MVT::SimpleValueType for each return type. Note that this
/// list is only populated when in the context of a target .td file. When
/// building Intrinsics.td, this isn't available, because we don't know
/// the target pointer size.
std::vector<MVT::SimpleValueType> RetVTs;
/// ArgTypeDefs - The records for each argument type. /// RetTypeDefs - The records for each return type.
/// std::vector<Record*> RetTypeDefs;
std::vector<Record*> ArgTypeDefs;
/// ParamVTs - The MVT::SimpleValueType for each parameter type. Note that
/// this list is only populated when in the context of a target .td file.
/// When building Intrinsics.td, this isn't available, because we don't
/// know the target pointer size.
std::vector<MVT::SimpleValueType> ParamVTs;
/// ParamTypeDefs - The records for each parameter type.
std::vector<Record*> ParamTypeDefs;
};
IntrinsicSignature IS;
// Memory mod/ref behavior of this intrinsic. // Memory mod/ref behavior of this intrinsic.
enum { enum {

View File

@ -438,25 +438,27 @@ CodeGenIntrinsic::CodeGenIntrinsic(Record *R) {
isCommutative = false; isCommutative = false;
if (DefName.size() <= 4 || if (DefName.size() <= 4 ||
std::string(DefName.begin(), DefName.begin()+4) != "int_") std::string(DefName.begin(), DefName.begin() + 4) != "int_")
throw "Intrinsic '" + DefName + "' does not start with 'int_'!"; throw "Intrinsic '" + DefName + "' does not start with 'int_'!";
EnumName = std::string(DefName.begin()+4, DefName.end()); EnumName = std::string(DefName.begin()+4, DefName.end());
if (R->getValue("GCCBuiltinName")) // Ignore a missing GCCBuiltinName field. if (R->getValue("GCCBuiltinName")) // Ignore a missing GCCBuiltinName field.
GCCBuiltinName = R->getValueAsString("GCCBuiltinName"); GCCBuiltinName = R->getValueAsString("GCCBuiltinName");
TargetPrefix = R->getValueAsString("TargetPrefix");
TargetPrefix = R->getValueAsString("TargetPrefix");
Name = R->getValueAsString("LLVMName"); Name = R->getValueAsString("LLVMName");
if (Name == "") { if (Name == "") {
// If an explicit name isn't specified, derive one from the DefName. // If an explicit name isn't specified, derive one from the DefName.
Name = "llvm."; Name = "llvm.";
for (unsigned i = 0, e = EnumName.size(); i != e; ++i) for (unsigned i = 0, e = EnumName.size(); i != e; ++i)
if (EnumName[i] == '_') Name += (EnumName[i] == '_') ? '.' : EnumName[i];
Name += '.';
else
Name += EnumName[i];
} else { } else {
// Verify it starts with "llvm.". // Verify it starts with "llvm.".
if (Name.size() <= 5 || if (Name.size() <= 5 ||
std::string(Name.begin(), Name.begin()+5) != "llvm.") std::string(Name.begin(), Name.begin() + 5) != "llvm.")
throw "Intrinsic '" + DefName + "'s name does not start with 'llvm.'!"; throw "Intrinsic '" + DefName + "'s name does not start with 'llvm.'!";
} }
@ -464,25 +466,36 @@ CodeGenIntrinsic::CodeGenIntrinsic(Record *R) {
// "llvm.<targetprefix>.". // "llvm.<targetprefix>.".
if (!TargetPrefix.empty()) { if (!TargetPrefix.empty()) {
if (Name.size() < 6+TargetPrefix.size() || if (Name.size() < 6+TargetPrefix.size() ||
std::string(Name.begin()+5, Name.begin()+6+TargetPrefix.size()) std::string(Name.begin() + 5, Name.begin() + 6 + TargetPrefix.size())
!= (TargetPrefix+".")) != (TargetPrefix + "."))
throw "Intrinsic '" + DefName + "' does not start with 'llvm." + throw "Intrinsic '" + DefName + "' does not start with 'llvm." +
TargetPrefix + ".'!"; TargetPrefix + ".'!";
} }
// Parse the list of argument types. // Parse the list of return types.
ListInit *TypeList = R->getValueAsListInit("Types"); ListInit *TypeList = R->getValueAsListInit("RetTypes");
for (unsigned i = 0, e = TypeList->getSize(); i != e; ++i) { for (unsigned i = 0, e = TypeList->getSize(); i != e; ++i) {
Record *TyEl = TypeList->getElementAsRecord(i); Record *TyEl = TypeList->getElementAsRecord(i);
assert(TyEl->isSubClassOf("LLVMType") && "Expected a type!"); assert(TyEl->isSubClassOf("LLVMType") && "Expected a type!");
MVT::SimpleValueType VT = getValueType(TyEl->getValueAsDef("VT")); MVT::SimpleValueType VT = getValueType(TyEl->getValueAsDef("VT"));
isOverloaded |= VT == MVT::iAny || VT == MVT::fAny || VT == MVT::iPTRAny; isOverloaded |= VT == MVT::iAny || VT == MVT::fAny || VT == MVT::iPTRAny;
ArgVTs.push_back(VT); IS.RetVTs.push_back(VT);
ArgTypeDefs.push_back(TyEl); IS.RetTypeDefs.push_back(TyEl);
} }
if (ArgVTs.size() == 0)
if (IS.RetVTs.size() == 0)
throw "Intrinsic '"+DefName+"' needs at least a type for the ret value!"; throw "Intrinsic '"+DefName+"' needs at least a type for the ret value!";
// Parse the list of parameter types.
TypeList = R->getValueAsListInit("ParamTypes");
for (unsigned i = 0, e = TypeList->getSize(); i != e; ++i) {
Record *TyEl = TypeList->getElementAsRecord(i);
assert(TyEl->isSubClassOf("LLVMType") && "Expected a type!");
MVT::SimpleValueType VT = getValueType(TyEl->getValueAsDef("VT"));
isOverloaded |= VT == MVT::iAny || VT == MVT::fAny || VT == MVT::iPTRAny;
IS.ParamVTs.push_back(VT);
IS.ParamTypeDefs.push_back(TyEl);
}
// Parse the intrinsic properties. // Parse the intrinsic properties.
ListInit *PropList = R->getValueAsListInit("Properties"); ListInit *PropList = R->getValueAsListInit("Properties");

View File

@ -138,7 +138,27 @@ static void EmitTypeForValueType(std::ostream &OS, MVT::SimpleValueType VT) {
} }
} }
static void EmitTypeGenerate(std::ostream &OS, Record *ArgType, static void EmitTypeGenerate(std::ostream &OS, const Record *ArgType,
unsigned &ArgNo);
static void EmitTypeGenerate(std::ostream &OS,
const std::vector<Record*> &ArgTypes,
unsigned &ArgNo) {
if (ArgTypes.size() == 1) {
EmitTypeGenerate(OS, ArgTypes.front(), ArgNo);
return;
}
OS << "StructType::get(";
for (std::vector<Record*>::const_iterator
I = ArgTypes.begin(), E = ArgTypes.end(); I != E; ++I)
EmitTypeGenerate(OS, *I, ArgNo);
OS << ", NULL)";
}
static void EmitTypeGenerate(std::ostream &OS, const Record *ArgType,
unsigned &ArgNo) { unsigned &ArgNo) {
MVT::SimpleValueType VT = getValueType(ArgType->getValueAsDef("VT")); MVT::SimpleValueType VT = getValueType(ArgType->getValueAsDef("VT"));
@ -184,17 +204,37 @@ static void EmitTypeGenerate(std::ostream &OS, Record *ArgType,
/// RecordListComparator - Provide a determinstic comparator for lists of /// RecordListComparator - Provide a determinstic comparator for lists of
/// records. /// records.
namespace { namespace {
typedef std::pair<std::vector<Record*>, std::vector<Record*> > RecPair;
struct RecordListComparator { struct RecordListComparator {
bool operator()(const std::vector<Record*> &LHS, bool operator()(const RecPair &LHS,
const std::vector<Record*> &RHS) const { const RecPair &RHS) const {
unsigned i = 0; unsigned i = 0;
do { const std::vector<Record*> *LHSVec = &LHS.first;
if (i == RHS.size()) return false; // RHS is shorter than LHS. const std::vector<Record*> *RHSVec = &RHS.first;
if (LHS[i] != RHS[i]) unsigned RHSSize = RHSVec->size();
return LHS[i]->getName() < RHS[i]->getName(); unsigned LHSSize = LHSVec->size();
} while (++i != LHS.size());
return i != RHS.size(); do {
if (i == RHSSize) return false; // RHS is shorter than LHS.
if ((*LHSVec)[i] != (*RHSVec)[i])
return (*LHSVec)[i]->getName() < (*RHSVec)[i]->getName();
} while (++i != LHSSize);
if (i != RHSSize) return false;
i = 0;
LHSVec = &LHS.second;
RHSVec = &RHS.second;
RHSSize = RHSVec->size();
LHSSize = LHSVec->size();
for (i = 0; i != LHSSize; ++i) {
if (i == RHSSize) return false; // RHS is shorter than LHS.
if ((*LHSVec)[i] != (*RHSVec)[i])
return (*LHSVec)[i]->getName() < (*RHSVec)[i]->getName();
}
return i != RHSSize;
} }
}; };
} }
@ -209,26 +249,33 @@ void IntrinsicEmitter::EmitVerifier(const std::vector<CodeGenIntrinsic> &Ints,
// This checking can emit a lot of very common code. To reduce the amount of // This checking can emit a lot of very common code. To reduce the amount of
// code that we emit, batch up cases that have identical types. This avoids // code that we emit, batch up cases that have identical types. This avoids
// problems where GCC can run out of memory compiling Verifier.cpp. // problems where GCC can run out of memory compiling Verifier.cpp.
typedef std::map<std::vector<Record*>, std::vector<unsigned>, typedef std::map<RecPair, std::vector<unsigned>, RecordListComparator> MapTy;
RecordListComparator> MapTy;
MapTy UniqueArgInfos; MapTy UniqueArgInfos;
// Compute the unique argument type info. // Compute the unique argument type info.
for (unsigned i = 0, e = Ints.size(); i != e; ++i) for (unsigned i = 0, e = Ints.size(); i != e; ++i)
UniqueArgInfos[Ints[i].ArgTypeDefs].push_back(i); UniqueArgInfos[make_pair(Ints[i].IS.RetTypeDefs,
Ints[i].IS.ParamTypeDefs)].push_back(i);
// Loop through the array, emitting one comparison for each batch. // Loop through the array, emitting one comparison for each batch.
for (MapTy::iterator I = UniqueArgInfos.begin(), for (MapTy::iterator I = UniqueArgInfos.begin(),
E = UniqueArgInfos.end(); I != E; ++I) { E = UniqueArgInfos.end(); I != E; ++I) {
for (unsigned i = 0, e = I->second.size(); i != e; ++i) { for (unsigned i = 0, e = I->second.size(); i != e; ++i)
OS << " case Intrinsic::" << Ints[I->second[i]].EnumName << ":\t\t// " OS << " case Intrinsic::" << Ints[I->second[i]].EnumName << ":\t\t// "
<< Ints[I->second[i]].Name << "\n"; << Ints[I->second[i]].Name << "\n";
}
const std::vector<Record*> &ArgTypes = I->first; const RecPair &ArgTypes = I->first;
OS << " VerifyIntrinsicPrototype(ID, IF, " << ArgTypes.size() << ", "; const std::vector<Record*> &RetTys = ArgTypes.first;
for (unsigned j = 0; j != ArgTypes.size(); ++j) { const std::vector<Record*> &ParamTys = ArgTypes.second;
Record *ArgType = ArgTypes[j];
OS << " VerifyIntrinsicPrototype(ID, IF, " << RetTys.size() << ", "
<< ParamTys.size();
// Emit return types.
for (unsigned j = 0, je = RetTys.size(); j != je; ++j) {
Record *ArgType = RetTys[j];
OS << ", ";
if (ArgType->isSubClassOf("LLVMMatchType")) { if (ArgType->isSubClassOf("LLVMMatchType")) {
unsigned Number = ArgType->getValueAsInt("Number"); unsigned Number = ArgType->getValueAsInt("Number");
assert(Number < j && "Invalid matching number!"); assert(Number < j && "Invalid matching number!");
@ -236,11 +283,28 @@ void IntrinsicEmitter::EmitVerifier(const std::vector<CodeGenIntrinsic> &Ints,
} else { } else {
MVT::SimpleValueType VT = getValueType(ArgType->getValueAsDef("VT")); MVT::SimpleValueType VT = getValueType(ArgType->getValueAsDef("VT"));
OS << getEnumName(VT); OS << getEnumName(VT);
if (VT == MVT::isVoid && j != 0 && j != ArgTypes.size()-1)
if (VT == MVT::isVoid && j != 0 && j != je - 1)
throw "Var arg type not last argument";
}
}
// Emit the parameter types.
for (unsigned j = 0, je = ParamTys.size(); j != je; ++j) {
Record *ArgType = ParamTys[j];
OS << ", ";
if (ArgType->isSubClassOf("LLVMMatchType")) {
unsigned Number = ArgType->getValueAsInt("Number");
assert(Number < j + RetTys.size() && "Invalid matching number!");
OS << "~" << Number;
} else {
MVT::SimpleValueType VT = getValueType(ArgType->getValueAsDef("VT"));
OS << getEnumName(VT);
if (VT == MVT::isVoid && j != 0 && j != je - 1)
throw "Var arg type not last argument"; throw "Var arg type not last argument";
} }
if (j != ArgTypes.size()-1)
OS << ", ";
} }
OS << ");\n"; OS << ");\n";
@ -259,43 +323,47 @@ void IntrinsicEmitter::EmitGenerator(const std::vector<CodeGenIntrinsic> &Ints,
// Similar to GET_INTRINSIC_VERIFIER, batch up cases that have identical // Similar to GET_INTRINSIC_VERIFIER, batch up cases that have identical
// types. // types.
typedef std::map<std::vector<Record*>, std::vector<unsigned>, typedef std::map<RecPair, std::vector<unsigned>, RecordListComparator> MapTy;
RecordListComparator> MapTy;
MapTy UniqueArgInfos; MapTy UniqueArgInfos;
// Compute the unique argument type info. // Compute the unique argument type info.
for (unsigned i = 0, e = Ints.size(); i != e; ++i) for (unsigned i = 0, e = Ints.size(); i != e; ++i)
UniqueArgInfos[Ints[i].ArgTypeDefs].push_back(i); UniqueArgInfos[make_pair(Ints[i].IS.RetTypeDefs,
Ints[i].IS.ParamTypeDefs)].push_back(i);
// Loop through the array, emitting one generator for each batch. // Loop through the array, emitting one generator for each batch.
for (MapTy::iterator I = UniqueArgInfos.begin(), for (MapTy::iterator I = UniqueArgInfos.begin(),
E = UniqueArgInfos.end(); I != E; ++I) { E = UniqueArgInfos.end(); I != E; ++I) {
for (unsigned i = 0, e = I->second.size(); i != e; ++i) { for (unsigned i = 0, e = I->second.size(); i != e; ++i)
OS << " case Intrinsic::" << Ints[I->second[i]].EnumName << ":\t\t// " OS << " case Intrinsic::" << Ints[I->second[i]].EnumName << ":\t\t// "
<< Ints[I->second[i]].Name << "\n"; << Ints[I->second[i]].Name << "\n";
}
const std::vector<Record*> &ArgTypes = I->first; const RecPair &ArgTypes = I->first;
unsigned N = ArgTypes.size(); const std::vector<Record*> &RetTys = ArgTypes.first;
const std::vector<Record*> &ParamTys = ArgTypes.second;
unsigned N = ParamTys.size();
if (N > 1 && if (N > 1 &&
getValueType(ArgTypes[N-1]->getValueAsDef("VT")) == MVT::isVoid) { getValueType(ParamTys[N - 1]->getValueAsDef("VT")) == MVT::isVoid) {
OS << " IsVarArg = true;\n"; OS << " IsVarArg = true;\n";
--N; --N;
} }
unsigned ArgNo = 0; unsigned ArgNo = 0;
OS << " ResultTy = "; OS << " ResultTy = ";
EmitTypeGenerate(OS, ArgTypes[0], ArgNo); EmitTypeGenerate(OS, RetTys, ArgNo);
OS << ";\n"; OS << ";\n";
for (unsigned j = 1; j != N; ++j) { for (unsigned j = 0; j != N; ++j) {
OS << " ArgTys.push_back("; OS << " ArgTys.push_back(";
EmitTypeGenerate(OS, ArgTypes[j], ArgNo); EmitTypeGenerate(OS, ParamTys[j], ArgNo);
OS << ");\n"; OS << ");\n";
} }
OS << " break;\n"; OS << " break;\n";
} }
OS << " }\n"; OS << " }\n";
OS << "#endif\n\n"; OS << "#endif\n\n";
} }