@@ -1296,6 +1296,7 @@ extern "C" {
1296
1296
#endif
1297
1297
(int ) DICompileUnit::DebugEmissionKind::FullDebug,
1298
1298
1 ,
1299
+ 1 ,
1299
1300
jl_rettype_inferred_addr, NULL };
1300
1301
}
1301
1302
@@ -1719,7 +1720,7 @@ jl_aliasinfo_t jl_aliasinfo_t::fromTBAA(jl_codectx_t &ctx, MDNode *tbaa) {
1719
1720
}
1720
1721
1721
1722
static Type *julia_type_to_llvm (jl_codectx_t &ctx, jl_value_t *jt, bool *isboxed = NULL );
1722
- static jl_returninfo_t get_specsig_function (jl_codectx_t &ctx, Module *M, Value *fval, StringRef name, jl_value_t *sig, jl_value_t *jlrettype, bool is_opaque_closure);
1723
+ static jl_returninfo_t get_specsig_function (jl_codectx_t &ctx, Module *M, Value *fval, StringRef name, jl_value_t *sig, jl_value_t *jlrettype, bool is_opaque_closure, bool gcstack_arg );
1723
1724
static jl_cgval_t emit_expr (jl_codectx_t &ctx, jl_value_t *expr, ssize_t ssaval = -1 );
1724
1725
static Value *global_binding_pointer (jl_codectx_t &ctx, jl_module_t *m, jl_sym_t *s,
1725
1726
jl_binding_t **pbnd, bool assign);
@@ -4107,7 +4108,8 @@ static jl_cgval_t emit_call_specfun_other(jl_codectx_t &ctx, bool is_opaque_clos
4107
4108
{
4108
4109
++EmittedSpecfunCalls;
4109
4110
// emit specialized call site
4110
- jl_returninfo_t returninfo = get_specsig_function (ctx, jl_Module, callee, specFunctionObject, specTypes, jlretty, is_opaque_closure);
4111
+ bool gcstack_arg = JL_FEAT_TEST (ctx, gcstack_arg);
4112
+ jl_returninfo_t returninfo = get_specsig_function (ctx, jl_Module, callee, specFunctionObject, specTypes, jlretty, is_opaque_closure, gcstack_arg);
4111
4113
FunctionType *cft = returninfo.decl .getFunctionType ();
4112
4114
*cc = returninfo.cc ;
4113
4115
*return_roots = returninfo.return_roots ;
@@ -4141,7 +4143,10 @@ static jl_cgval_t emit_call_specfun_other(jl_codectx_t &ctx, bool is_opaque_clos
4141
4143
argvals[idx] = return_roots;
4142
4144
idx++;
4143
4145
}
4144
-
4146
+ if (gcstack_arg) {
4147
+ argvals[idx] = ctx.pgcstack ;
4148
+ idx++;
4149
+ }
4145
4150
for (size_t i = 0 ; i < nargs; i++) {
4146
4151
jl_value_t *jt = jl_nth_slot_type (specTypes, i);
4147
4152
// n.b.: specTypes is required to be a datatype by construction for specsig
@@ -4205,6 +4210,8 @@ static jl_cgval_t emit_call_specfun_other(jl_codectx_t &ctx, bool is_opaque_clos
4205
4210
}
4206
4211
CallInst *call = ctx.builder .CreateCall (cft, TheCallee, argvals);
4207
4212
call->setAttributes (returninfo.attrs );
4213
+ if (gcstack_arg)
4214
+ call->setCallingConv (CallingConv::Swift);
4208
4215
4209
4216
jl_cgval_t retval;
4210
4217
switch (returninfo.cc ) {
@@ -5273,7 +5280,7 @@ static std::pair<Function*, Function*> get_oc_function(jl_codectx_t &ctx, jl_met
5273
5280
specF = closure_m.getModuleUnlocked ()->getFunction (closure_decls.specFunctionObject );
5274
5281
if (specF) {
5275
5282
jl_returninfo_t returninfo = get_specsig_function (ctx, jl_Module, NULL ,
5276
- closure_decls.specFunctionObject , sigtype, rettype, true );
5283
+ closure_decls.specFunctionObject , sigtype, rettype, true , JL_FEAT_TEST (ctx,gcstack_arg) );
5277
5284
specF = cast<Function>(returninfo.decl .getCallee ());
5278
5285
}
5279
5286
}
@@ -5786,13 +5793,15 @@ static void emit_cfunc_invalidate(
5786
5793
DebugLoc noDbg;
5787
5794
ctx.builder .SetCurrentDebugLocation (noDbg);
5788
5795
allocate_gc_frame (ctx, b0);
5789
-
5790
5796
Function::arg_iterator AI = gf_thunk->arg_begin ();
5791
5797
SmallVector<jl_cgval_t > myargs (nargs);
5792
5798
if (cc == jl_returninfo_t ::SRet || cc == jl_returninfo_t ::Union)
5793
5799
++AI;
5794
5800
if (return_roots)
5795
5801
++AI;
5802
+ if (JL_FEAT_TEST (ctx,gcstack_arg)){
5803
+ ++AI; // gcstack_arg
5804
+ }
5796
5805
for (size_t i = 0 ; i < nargs; i++) {
5797
5806
jl_value_t *jt = jl_nth_slot_type (calltype, i);
5798
5807
// n.b. specTypes is required to be a datatype by construction for specsig
@@ -6258,8 +6267,9 @@ static Function* gen_cfun_wrapper(
6258
6267
bool is_opaque_closure = jl_is_method (lam->def .value ) && lam->def .method ->is_for_opaque_closure ;
6259
6268
assert (calltype == 3 );
6260
6269
// emit a specsig call
6270
+ bool gcstack_arg = JL_FEAT_TEST (ctx, gcstack_arg);
6261
6271
StringRef protoname = jl_ExecutionEngine->getFunctionAtAddress ((uintptr_t )callptr, codeinst);
6262
- jl_returninfo_t returninfo = get_specsig_function (ctx, M, NULL , protoname, lam->specTypes , astrt, is_opaque_closure);
6272
+ jl_returninfo_t returninfo = get_specsig_function (ctx, M, NULL , protoname, lam->specTypes , astrt, is_opaque_closure, gcstack_arg );
6263
6273
FunctionType *cft = returninfo.decl .getFunctionType ();
6264
6274
jlfunc_sret = (returninfo.cc == jl_returninfo_t ::SRet);
6265
6275
@@ -6286,6 +6296,8 @@ static Function* gen_cfun_wrapper(
6286
6296
AllocaInst *return_roots = emit_static_alloca (ctx, get_returnroots_type (ctx, returninfo.return_roots ));
6287
6297
args.push_back (return_roots);
6288
6298
}
6299
+ if (gcstack_arg)
6300
+ args.push_back (ctx.pgcstack );
6289
6301
for (size_t i = 0 ; i < nargs + 1 ; i++) {
6290
6302
// figure out how to repack the arguments
6291
6303
jl_cgval_t &inputarg = inputargs[i];
@@ -6332,11 +6344,15 @@ static Function* gen_cfun_wrapper(
6332
6344
emit_cfunc_invalidate (gf_thunk, returninfo.cc , returninfo.return_roots , lam->specTypes , codeinst->rettype , is_opaque_closure, nargs + 1 , ctx.emission_context );
6333
6345
theFptr = ctx.builder .CreateSelect (age_ok, theFptr, gf_thunk);
6334
6346
}
6347
+
6335
6348
assert (cast<PointerType>(theFptr->getType ())->isOpaqueOrPointeeTypeMatches (returninfo.decl .getFunctionType ()));
6336
6349
CallInst *call = ctx.builder .CreateCall (
6337
6350
returninfo.decl .getFunctionType (),
6338
6351
theFptr, ArrayRef<Value*>(args));
6339
6352
call->setAttributes (returninfo.attrs );
6353
+ if (gcstack_arg)
6354
+ call->setCallingConv (CallingConv::Swift);
6355
+
6340
6356
switch (returninfo.cc ) {
6341
6357
case jl_returninfo_t ::Boxed:
6342
6358
retval = mark_julia_type (ctx, call, true , astrt);
@@ -6710,7 +6726,11 @@ static Function *gen_invoke_wrapper(jl_method_instance_t *lam, jl_value_t *jlret
6710
6726
args[idx] = return_roots;
6711
6727
idx++;
6712
6728
}
6713
-
6729
+ bool gcstack_arg = JL_FEAT_TEST (ctx, gcstack_arg);
6730
+ if (gcstack_arg) {
6731
+ args[idx] = ctx.pgcstack ;
6732
+ idx++;
6733
+ }
6714
6734
bool is_opaque_closure = jl_is_method (lam->def .value ) && lam->def .method ->is_for_opaque_closure ;
6715
6735
for (size_t i = 0 ; i < jl_nparams (lam->specTypes ) && idx < nfargs; ++i) {
6716
6736
jl_value_t *ty = ((i == 0 ) && is_opaque_closure) ? (jl_value_t *)jl_any_type :
@@ -6748,7 +6768,8 @@ static Function *gen_invoke_wrapper(jl_method_instance_t *lam, jl_value_t *jlret
6748
6768
}
6749
6769
CallInst *call = ctx.builder .CreateCall (f.decl , args);
6750
6770
call->setAttributes (f.attrs );
6751
-
6771
+ if (gcstack_arg)
6772
+ call->setCallingConv (CallingConv::Swift);
6752
6773
jl_cgval_t retval;
6753
6774
if (retarg != -1 ) {
6754
6775
Value *theArg;
@@ -6790,7 +6811,7 @@ static Function *gen_invoke_wrapper(jl_method_instance_t *lam, jl_value_t *jlret
6790
6811
return w;
6791
6812
}
6792
6813
6793
- static jl_returninfo_t get_specsig_function (jl_codectx_t &ctx, Module *M, Value *fval, StringRef name, jl_value_t *sig, jl_value_t *jlrettype, bool is_opaque_closure)
6814
+ static jl_returninfo_t get_specsig_function (jl_codectx_t &ctx, Module *M, Value *fval, StringRef name, jl_value_t *sig, jl_value_t *jlrettype, bool is_opaque_closure, bool gcstack_arg )
6794
6815
{
6795
6816
jl_returninfo_t props = {};
6796
6817
SmallVector<Type*, 8 > fsig;
@@ -6875,6 +6896,14 @@ static jl_returninfo_t get_specsig_function(jl_codectx_t &ctx, Module *M, Value
6875
6896
fsig.push_back (get_returnroots_type (ctx, props.return_roots )->getPointerTo (0 ));
6876
6897
}
6877
6898
6899
+ if (gcstack_arg){
6900
+ AttrBuilder param (ctx.builder .getContext ());
6901
+ param.addAttribute (Attribute::SwiftSelf);
6902
+ param.addAttribute (Attribute::NonNull);
6903
+ attrs.push_back (AttributeSet::get (ctx.builder .getContext (), param));
6904
+ fsig.push_back (PointerType::get (JuliaType::get_ppjlvalue_ty (ctx.builder .getContext ()), 0 ));
6905
+ }
6906
+
6878
6907
for (size_t i = 0 ; i < jl_nparams (sig); i++) {
6879
6908
jl_value_t *jt = jl_tparam (sig, i);
6880
6909
bool isboxed = false ;
@@ -6936,7 +6965,8 @@ static jl_returninfo_t get_specsig_function(jl_codectx_t &ctx, Module *M, Value
6936
6965
else
6937
6966
fval = emit_bitcast (ctx, fval, ftype->getPointerTo ());
6938
6967
}
6939
-
6968
+ if (gcstack_arg && isa<Function>(fval))
6969
+ cast<Function>(fval)->setCallingConv (CallingConv::Swift);
6940
6970
props.decl = FunctionCallee (ftype, fval);
6941
6971
props.attrs = attributes;
6942
6972
return props;
@@ -7163,7 +7193,8 @@ static jl_llvm_functions_t
7163
7193
Function *f = NULL ;
7164
7194
bool has_sret = false ;
7165
7195
if (specsig) { // assumes !va and !needsparams
7166
- returninfo = get_specsig_function (ctx, M, NULL , declarations.specFunctionObject , lam->specTypes , jlrettype, ctx.is_opaque_closure );
7196
+ returninfo = get_specsig_function (ctx, M, NULL , declarations.specFunctionObject , lam->specTypes ,
7197
+ jlrettype, ctx.is_opaque_closure , JL_FEAT_TEST (ctx,gcstack_arg));
7167
7198
f = cast<Function>(returninfo.decl .getCallee ());
7168
7199
has_sret = (returninfo.cc == jl_returninfo_t ::SRet || returninfo.cc == jl_returninfo_t ::Union);
7169
7200
jl_init_function (f, ctx.emission_context .TargetTriple );
@@ -7348,7 +7379,6 @@ static jl_llvm_functions_t
7348
7379
ctx.spvals_ptr = &*AI++;
7349
7380
}
7350
7381
}
7351
-
7352
7382
// step 6. set up GC frame
7353
7383
allocate_gc_frame (ctx, b0);
7354
7384
Value *last_age = NULL ;
@@ -7554,6 +7584,12 @@ static jl_llvm_functions_t
7554
7584
param.addAlignmentAttr (Align (sizeof (jl_value_t *)));
7555
7585
attrs.at (Arg->getArgNo ()) = AttributeSet::get (Arg->getContext (), param); // function declaration attributes
7556
7586
}
7587
+ if (specsig && JL_FEAT_TEST (ctx, gcstack_arg)){
7588
+ Argument *Arg = &*AI;
7589
+ ++AI;
7590
+ AttrBuilder param (ctx.builder .getContext ());
7591
+ attrs.at (Arg->getArgNo ()) = AttributeSet::get (Arg->getContext (), param);
7592
+ }
7557
7593
for (i = 0 ; i < nreq; i++) {
7558
7594
jl_sym_t *s = slot_symbol (ctx, i);
7559
7595
jl_value_t *argType = jl_nth_slot_type (lam->specTypes , i);
@@ -8564,7 +8600,7 @@ static jl_llvm_functions_t jl_emit_oc_wrapper(orc::ThreadSafeModule &m, jl_codeg
8564
8600
jl_llvm_functions_t declarations;
8565
8601
declarations.functionObject = " jl_f_opaque_closure_call" ;
8566
8602
if (uses_specsig (mi->specTypes , false , true , rettype, true )) {
8567
- jl_returninfo_t returninfo = get_specsig_function (ctx, M, NULL , funcName, mi->specTypes , rettype, 1 );
8603
+ jl_returninfo_t returninfo = get_specsig_function (ctx, M, NULL , funcName, mi->specTypes , rettype, true , JL_FEAT_TEST (ctx,gcstack_arg) );
8568
8604
Function *gf_thunk = cast<Function>(returninfo.decl .getCallee ());
8569
8605
jl_init_function (gf_thunk, ctx.emission_context .TargetTriple );
8570
8606
size_t nrealargs = jl_nparams (mi->specTypes );
0 commit comments