From 8f1218adf230dfdd721a69ef6ad1d86f67368bea Mon Sep 17 00:00:00 2001 From: Thomas Faingnaert Date: Fri, 14 Feb 2020 15:01:04 +0100 Subject: [PATCH] Add AddrSpacePtr type (cherry picked from commit 8cb8f0c485a81082813dde82b7caba29e2343c36) --- base/refpointer.jl | 8 ++++++++ src/builtins.c | 1 + src/ccall.cpp | 5 +++++ src/cgutils.cpp | 13 +++++++++++++ src/jltypes.c | 11 +++++++++++ src/julia.h | 8 ++++++++ src/staticdata.c | 4 ++-- test/llvmpasses/llvmcall.jl | 3 +++ 8 files changed, 51 insertions(+), 2 deletions(-) diff --git a/base/refpointer.jl b/base/refpointer.jl index b12886b6a5373..56817bb046ff6 100644 --- a/base/refpointer.jl +++ b/base/refpointer.jl @@ -132,3 +132,11 @@ getindex(b::RefArray) = b.x[b.i] setindex!(b::RefArray, x) = (b.x[b.i] = x; b) ### + +""" + AddrSpacePtr{T, AS} + +When passed as a `ccall` argument with the `llvmcall` calling convention, an `AddrSpacePtr` will be converted to an LLVM pointer type with the correct address space. +This type is mainly used to ensure Julia's codegen uses the correct address space when calling LLVM intrinsics. +""" +Core.AddrSpacePtr diff --git a/src/builtins.c b/src/builtins.c index 2ffd1c95e8c21..82209c2f1ba1e 100644 --- a/src/builtins.c +++ b/src/builtins.c @@ -1373,6 +1373,7 @@ void jl_init_primitives(void) JL_GC_DISABLED add_builtin("CodeInfo", (jl_value_t*)jl_code_info_type); add_builtin("Ref", (jl_value_t*)jl_ref_type); add_builtin("Ptr", (jl_value_t*)jl_pointer_type); + add_builtin("AddrSpacePtr", (jl_value_t*)jl_addrspace_pointer_type); add_builtin("Task", (jl_value_t*)jl_task_type); add_builtin("AbstractArray", (jl_value_t*)jl_abstractarray_type); diff --git a/src/ccall.cpp b/src/ccall.cpp index 66c58a0e26ca0..c820020796526 100644 --- a/src/ccall.cpp +++ b/src/ccall.cpp @@ -1145,6 +1145,11 @@ std::string generate_func_sig(const char *fname) t = T_pint8; isboxed = false; } + else if (llvmcall && jl_is_addrspace_ptr_type(tti)) { + t = bitstype_to_llvm(tti, true); + tti = (jl_value_t*)jl_voidpointer_type; + isboxed = false; + } else { if (jl_is_primitivetype(tti)) { // see pull req #978. need to annotate signext/zeroext for diff --git a/src/cgutils.cpp b/src/cgutils.cpp index d5944326d6ee7..d204975bb27d1 100644 --- a/src/cgutils.cpp +++ b/src/cgutils.cpp @@ -571,6 +571,19 @@ static Type *bitstype_to_llvm(jl_value_t *bt, bool llvmcall = false) return T_float32; if (bt == (jl_value_t*)jl_float64_type) return T_float64; + if (jl_is_addrspace_ptr_type(bt)) { + int as = 0; + + jl_datatype_t *typ = (jl_datatype_t*)bt; + jl_value_t *as_param = jl_svecref(typ->parameters, 1); + + if (jl_is_int32(as_param)) + as = jl_unbox_int32(as_param); + else if (jl_is_int64(as_param)) + as = jl_unbox_int64(as_param); + + return PointerType::get(T_int8, as); + } int nb = jl_datatype_size(bt); return Type::getIntNTy(jl_LLVMContext, nb * 8); } diff --git a/src/jltypes.c b/src/jltypes.c index 3873a9e4ede72..84c48848bc48d 100644 --- a/src/jltypes.c +++ b/src/jltypes.c @@ -115,6 +115,8 @@ jl_datatype_t *jl_lineinfonode_type; jl_unionall_t *jl_ref_type; jl_unionall_t *jl_pointer_type; jl_typename_t *jl_pointer_typename; +jl_unionall_t *jl_addrspace_pointer_type; +jl_typename_t *jl_addrspace_pointer_typename; jl_datatype_t *jl_void_type; jl_datatype_t *jl_voidpointer_type; jl_typename_t *jl_namedtuple_typename; @@ -2234,6 +2236,15 @@ void jl_init_types(void) JL_GC_DISABLED sizeof(void*)*8)->name->wrapper; jl_pointer_typename = ((jl_datatype_t*)jl_unwrap_unionall((jl_value_t*)jl_pointer_type))->name; + // AddrSpacePtr{T, AS} where {T, AS} + tv = jl_svec2(tvar("T"), tvar("AS")); + jl_svec_t *tv_base = jl_svec1(tvar("T")); + jl_addrspace_pointer_type = (jl_unionall_t*) + jl_new_primitivetype((jl_value_t*)jl_symbol("AddrSpacePtr"), core, + (jl_datatype_t*)jl_apply_type((jl_value_t*)jl_ref_type, jl_svec_data(tv_base), 1), tv, + sizeof(void*)*8)->name->wrapper; + jl_addrspace_pointer_typename = ((jl_datatype_t*)jl_unwrap_unionall((jl_value_t*)jl_addrspace_pointer_type))->name; + // Type{T} where T<:Tuple tttvar = jl_new_typevar(jl_symbol("T"), (jl_value_t*)jl_bottom_type, diff --git a/src/julia.h b/src/julia.h index e4e6403945b95..6333ce5101269 100644 --- a/src/julia.h +++ b/src/julia.h @@ -644,8 +644,10 @@ extern JL_DLLEXPORT jl_datatype_t *jl_void_type JL_GLOBALLY_ROOTED; extern JL_DLLEXPORT jl_datatype_t *jl_signed_type JL_GLOBALLY_ROOTED; extern JL_DLLEXPORT jl_datatype_t *jl_voidpointer_type JL_GLOBALLY_ROOTED; extern JL_DLLEXPORT jl_unionall_t *jl_pointer_type JL_GLOBALLY_ROOTED; +extern JL_DLLEXPORT jl_unionall_t *jl_addrspace_pointer_type JL_GLOBALLY_ROOTED; extern JL_DLLEXPORT jl_unionall_t *jl_ref_type JL_GLOBALLY_ROOTED; extern JL_DLLEXPORT jl_typename_t *jl_pointer_typename JL_GLOBALLY_ROOTED; +extern JL_DLLEXPORT jl_typename_t *jl_addrspace_pointer_typename JL_GLOBALLY_ROOTED; extern JL_DLLEXPORT jl_typename_t *jl_namedtuple_typename JL_GLOBALLY_ROOTED; extern JL_DLLEXPORT jl_unionall_t *jl_namedtuple_type JL_GLOBALLY_ROOTED; extern JL_DLLEXPORT jl_datatype_t *jl_task_type JL_GLOBALLY_ROOTED; @@ -1159,6 +1161,12 @@ STATIC_INLINE int jl_is_cpointer_type(jl_value_t *t) JL_NOTSAFEPOINT ((jl_datatype_t*)(t))->name == ((jl_datatype_t*)jl_pointer_type->body)->name); } +STATIC_INLINE int jl_is_addrspace_ptr_type(jl_value_t *t) JL_NOTSAFEPOINT +{ + return (jl_is_datatype(t) && + ((jl_datatype_t*)(t))->name == jl_addrspace_pointer_typename); +} + STATIC_INLINE int jl_is_abstract_ref_type(jl_value_t *t) JL_NOTSAFEPOINT { return (jl_is_datatype(t) && diff --git a/src/staticdata.c b/src/staticdata.c index e789713d4f39b..554a67b1cbfdf 100644 --- a/src/staticdata.c +++ b/src/staticdata.c @@ -41,7 +41,7 @@ static void *const _tags[] = { &jl_linenumbernode_type, &jl_lineinfonode_type, &jl_gotonode_type, &jl_quotenode_type, &jl_pinode_type, &jl_phinode_type, &jl_phicnode_type, &jl_upsilonnode_type, - &jl_type_type, &jl_bottom_type, &jl_ref_type, &jl_pointer_type, + &jl_type_type, &jl_bottom_type, &jl_ref_type, &jl_pointer_type, &jl_addrspace_pointer_type, &jl_vararg_type, &jl_abstractarray_type, &jl_densearray_type, &jl_void_type, &jl_function_type, &jl_typeofbottom_type, &jl_unionall_type, &jl_typename_type, &jl_builtin_type, &jl_code_info_type, @@ -57,7 +57,7 @@ static void *const _tags[] = { &jl_float16_type, &jl_float32_type, &jl_float64_type, &jl_floatingpoint_type, &jl_number_type, &jl_signed_type, // special typenames - &jl_tuple_typename, &jl_pointer_typename, &jl_array_typename, &jl_type_typename, + &jl_tuple_typename, &jl_pointer_typename, &jl_addrspace_pointer_typename, &jl_array_typename, &jl_type_typename, &jl_vararg_typename, &jl_namedtuple_typename, &jl_vecelement_typename, // special exceptions diff --git a/test/llvmpasses/llvmcall.jl b/test/llvmpasses/llvmcall.jl index 944b19877c43e..13d7f63b14d9c 100644 --- a/test/llvmpasses/llvmcall.jl +++ b/test/llvmpasses/llvmcall.jl @@ -17,5 +17,8 @@ emit(foo, NTuple{2, Float16}) # CHECK: call <2 x half> @foo(<2 x half> %{{[0-9]+}}) emit(foo, NTuple{2, VecElement{Float16}}) +# CHECK: call i8 addrspace(3)* @foo(i8 addrspace(3)* %{{[0-9]+}}) +emit(foo, Core.AddrSpacePtr{Float32, 3}) + # CHECK: define <2 x i16> @julia_bar_{{[0-9]+}}([2 x i16] emit(bar, NTuple{2, Float16})