Skip to content

Commit

Permalink
Merge pull request JuliaLang#23581 from JuliaLang/tb/inflight
Browse files Browse the repository at this point in the history
Fix and improve codegen params
  • Loading branch information
maleadt committed Sep 5, 2017
2 parents bc68f48 + c31fdea commit 8183c0f
Show file tree
Hide file tree
Showing 6 changed files with 31 additions and 88 deletions.
30 changes: 8 additions & 22 deletions base/reflection.jl
Original file line number Diff line number Diff line change
Expand Up @@ -724,41 +724,27 @@ function method_instances(@nospecialize(f), @nospecialize(t), world::UInt = type
return results
end

# this type mirrors jl_cghooks_t (documented in julia.h)
struct CodegenHooks
module_setup::Ptr{Void}
module_activation::Ptr{Void}
raise_exception::Ptr{Void}

CodegenHooks(;module_setup=nothing, module_activation=nothing, raise_exception=nothing) =
new(pointer_from_objref(module_setup),
pointer_from_objref(module_activation),
pointer_from_objref(raise_exception))
end

# this type mirrors jl_cgparams_t (documented in julia.h)
struct CodegenParams
cached::Cint

runtime::Cint
exceptions::Cint
track_allocations::Cint
code_coverage::Cint
static_alloc::Cint
dynamic_alloc::Cint
prefer_specsig::Cint

hooks::CodegenHooks
module_setup::Any
module_activation::Any
raise_exception::Any

CodegenParams(;cached::Bool=true,
runtime::Bool=true, exceptions::Bool=true,
track_allocations::Bool=true, code_coverage::Bool=true,
static_alloc::Bool=true, dynamic_alloc::Bool=true,
hooks::CodegenHooks=CodegenHooks()) =
static_alloc::Bool=true, prefer_specsig::Bool=false,
module_setup=nothing, module_activation=nothing, raise_exception=nothing) =
new(Cint(cached),
Cint(runtime), Cint(exceptions),
Cint(track_allocations), Cint(code_coverage),
Cint(static_alloc), Cint(dynamic_alloc),
hooks)
Cint(static_alloc), Cint(prefer_specsig),
module_setup, module_activation, raise_exception)
end

# Printing code representations in IR and assembly
Expand Down
6 changes: 0 additions & 6 deletions src/ccall.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1513,12 +1513,6 @@ static jl_cgval_t emit_ccall(jl_codectx_t &ctx, jl_value_t **args, size_t nargs)
rt = (jl_value_t*)jl_any_type; // convert return type to jl_value_t*
}

// check if we require the runtime
// TODO: could be more fine-grained,
// respecting special functions below that don't require the runtime
if (!llvmcall && (!f_lib || f_lib == JL_DL_LIBNAME))
JL_FEAT_REQUIRE(ctx, runtime);

// some sanity checking and check whether there's a vararg
bool isVa;
size_t nargt;
Expand Down
24 changes: 6 additions & 18 deletions src/cgutils.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -97,22 +97,15 @@ static Value *mark_callee_rooted(IRBuilder<> &irbuilder, Value *V)

// --- language feature checks ---

// branch on whether a language feature is enabled or not
#define JL_FEAT_TEST(ctx, feature) ((ctx).params->feature)

// require a language feature to be enabled
#define JL_FEAT_REQUIRE(ctx, feature) \
if (!JL_FEAT_TEST(ctx, feature)) \
jl_errorf("%s for %s:%d requires the " #feature " language feature, which is disabled", \
__FUNCTION__, (ctx).file.str().c_str(), *(ctx).line);


// --- hook checks ---

#define JL_HOOK_TEST(params,hook) ((params)->hooks.hook != jl_nothing)
#define JL_HOOK_TEST(params,hook) ((params)->hook != jl_nothing)

#define JL_HOOK_CALL(params,hook,argc,...) \
_hook_call<argc>((params)->hooks.hook, {{__VA_ARGS__}});
_hook_call<argc>((params)->hook, {{__VA_ARGS__}});
template<int N>
static inline void _hook_call(jl_value_t *hook, std::array<jl_value_t*,N> args) {
jl_value_t **argv;
Expand Down Expand Up @@ -907,7 +900,6 @@ static void raise_exception(jl_codectx_t &ctx, Value *exc,
jl_box_voidpointer(wrap(ctx.builder.GetInsertBlock())),
jl_box_voidpointer(wrap(exc)));
} else {
JL_FEAT_REQUIRE(ctx, runtime);
ctx.builder.CreateCall(prepare_call(jlthrow_func), { mark_callee_rooted(exc) });
}
ctx.builder.CreateUnreachable();
Expand Down Expand Up @@ -2116,8 +2108,6 @@ static void emit_cpointercheck(jl_codectx_t &ctx, const jl_cgval_t &x, const std
// allocation for known size object
static Value *emit_allocobj(jl_codectx_t &ctx, size_t static_size, Value *jt)
{
JL_FEAT_REQUIRE(ctx, dynamic_alloc);
JL_FEAT_REQUIRE(ctx, runtime);
Value *ptls_ptr = emit_bitcast(ctx, ctx.ptlsStates, T_pint8);
auto call = ctx.builder.CreateCall(prepare_call(jl_alloc_obj_func),
{ptls_ptr, ConstantInt::get(T_size, static_size),
Expand Down Expand Up @@ -2348,14 +2338,12 @@ static int compare_cgparams(const jl_cgparams_t *a, const jl_cgparams_t *b)
{
return (a->cached == b->cached) &&
// language features
(a->runtime == b->runtime) &&
(a->exceptions == b->exceptions) &&
(a->track_allocations == b->track_allocations) &&
(a->code_coverage == b->code_coverage) &&
(a->static_alloc == b->static_alloc) &&
(a->dynamic_alloc == b->dynamic_alloc) &&
(a->prefer_specsig == b->prefer_specsig) &&
// hooks
(a->hooks.module_setup == b->hooks.module_setup) &&
(a->hooks.module_activation == b->hooks.module_activation) &&
(a->hooks.raise_exception == b->hooks.raise_exception);
(a->module_setup == b->module_setup) &&
(a->module_activation == b->module_activation) &&
(a->raise_exception == b->raise_exception);
}
27 changes: 4 additions & 23 deletions src/codegen.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2204,7 +2204,6 @@ static Value *emit_f_is(jl_codectx_t &ctx, const jl_cgval_t &arg1, const jl_cgva
decay_derived(varg2));
}

JL_FEAT_REQUIRE(ctx, runtime);
Value *varg1 = mark_callee_rooted(boxed(ctx, arg1));
Value *varg2 = mark_callee_rooted(boxed(ctx, arg2));
return ctx.builder.CreateTrunc(ctx.builder.CreateCall(prepare_call(jlegal_func), {varg1, varg2}), T_int1);
Expand Down Expand Up @@ -2249,7 +2248,6 @@ static bool emit_builtin_call(jl_codectx_t &ctx, jl_cgval_t *ret, jl_value_t *f,
if (jl_subtype(ty.typ, (jl_value_t*)jl_type_type)) {
Value *rt_arg = boxed(ctx, arg);
Value *rt_ty = boxed(ctx, ty);
JL_FEAT_REQUIRE(ctx, runtime);
ctx.builder.CreateCall(prepare_call(jltypeassert_func), {rt_arg, rt_ty});
*ret = arg;
return true;
Expand Down Expand Up @@ -2290,7 +2288,6 @@ static bool emit_builtin_call(jl_codectx_t &ctx, jl_cgval_t *ret, jl_value_t *f,
nva = ctx.builder.CreateTrunc(nva, T_int32);
#endif
Value *theArgs = ctx.builder.CreateGEP(ctx.argArray, ConstantInt::get(T_size, ctx.nReqArgs));
JL_FEAT_REQUIRE(ctx, runtime);
Value *r = ctx.builder.CreateCall(prepare_call(jlapply2va_func), { theF, theArgs, nva });
*ret = mark_julia_type(ctx, r, true, jl_any_type);
return true;
Expand Down Expand Up @@ -2955,7 +2952,6 @@ static jl_cgval_t emit_invoke(jl_codectx_t &ctx, jl_expr_t *ex)
}
}
}
JL_FEAT_REQUIRE(ctx, runtime);
jl_cgval_t result = mark_julia_type(ctx,
emit_jlcall(
ctx,
Expand Down Expand Up @@ -3007,16 +3003,6 @@ static jl_cgval_t emit_call(jl_codectx_t &ctx, jl_expr_t *ex)
}
}

if (!JL_FEAT_TEST(ctx, runtime)) {
char* name = NULL;
if (jl_is_symbol(args[0]))
name = jl_symbol_name((jl_sym_t*)args[0]);
if (jl_is_globalref(args[0]))
name = jl_symbol_name(jl_globalref_name(args[0]));
jl_errorf("generic call to %s requires the runtime language feature",
name ? name : "<unknown>");
}

// emit function and arguments
Value *callval = emit_jlcall(ctx, jlapplygeneric_func, nullptr, argv, nargs);
return mark_julia_type(ctx, callval, true, rt);
Expand Down Expand Up @@ -3059,7 +3045,6 @@ static Value *global_binding_pointer(jl_codectx_t &ctx, jl_module_t *m, jl_sym_t
b = jl_get_binding(m, s);
if (b == NULL) {
// var not found. switch to delayed lookup.
JL_FEAT_REQUIRE(ctx, runtime);
std::stringstream name;
name << "delayedvar" << globalUnique++;
Constant *initnul = V_null;
Expand Down Expand Up @@ -3417,7 +3402,6 @@ static void emit_assignment(jl_codectx_t &ctx, jl_value_t *l, jl_value_t *r)
if (bp == NULL && s != NULL)
bp = global_binding_pointer(ctx, ctx.module, s, &bnd, true);
if (bp != NULL) { // it's a global
JL_FEAT_REQUIRE(ctx, runtime);
assert(bnd);
Value *rval = mark_callee_rooted(boxed(ctx, emit_expr(ctx, r)));
ctx.builder.CreateCall(prepare_call(jlcheckassign_func),
Expand Down Expand Up @@ -3623,7 +3607,6 @@ static void emit_stmtpos(jl_codectx_t &ctx, jl_value_t *expr)
}
else if (head == leave_sym) {
assert(jl_is_long(args[0]));
JL_FEAT_REQUIRE(ctx, runtime);
ctx.builder.CreateCall(prepare_call(jlleave_func),
ConstantInt::get(T_int32, jl_unbox_long(args[0])));
}
Expand Down Expand Up @@ -3733,7 +3716,6 @@ static jl_cgval_t emit_expr(jl_codectx_t &ctx, jl_value_t *expr)
else if (head == method_sym) {
jl_value_t *mn = args[0];
assert(jl_expr_nargs(ex) != 1 || jl_is_symbol(mn) || jl_is_slot(mn));
JL_FEAT_REQUIRE(ctx, runtime);

Value *bp = NULL, *name, *bp_owner = V_null;
jl_binding_t *bnd = NULL;
Expand Down Expand Up @@ -3800,7 +3782,6 @@ static jl_cgval_t emit_expr(jl_codectx_t &ctx, jl_value_t *expr)
sym = jl_globalref_name(sym);
}
if (jl_is_symbol(sym)) {
JL_FEAT_REQUIRE(ctx, runtime);
jl_binding_t *bnd = NULL;
(void)global_binding_pointer(ctx, mod, sym, &bnd, true); assert(bnd);
ctx.builder.CreateCall(prepare_call(jldeclareconst_func),
Expand Down Expand Up @@ -3830,7 +3811,6 @@ static jl_cgval_t emit_expr(jl_codectx_t &ctx, jl_value_t *expr)
true, jl_any_type);
}
else if (head == copyast_sym) {
JL_FEAT_REQUIRE(ctx, runtime);
jl_value_t *arg = args[0];
if (jl_is_quotenode(arg)) {
jl_value_t *arg1 = jl_fieldref(arg, 0);
Expand Down Expand Up @@ -3868,7 +3848,6 @@ static jl_cgval_t emit_expr(jl_codectx_t &ctx, jl_value_t *expr)
jl_error("syntax: prefix \"$\" in non-quoted expression");
if (jl_is_toplevel_only_expr(expr) &&
!jl_is_method(ctx.linfo->def.method)) {
JL_FEAT_REQUIRE(ctx, runtime);
// call interpreter to run a toplevel expr from inside a
// compiled toplevel thunk.
Value *args[2] = {
Expand Down Expand Up @@ -4563,7 +4542,7 @@ static Function *gen_jlcall_wrapper(jl_method_instance_t *lam, const jl_returnin
return w;
}

static bool uses_specsig(jl_value_t *sig, jl_value_t *rettype, bool needsparam, bool va, jl_code_info_t *src)
static bool uses_specsig(jl_value_t *sig, jl_value_t *rettype, bool needsparam, bool va, jl_code_info_t *src, bool prefer_specsig)
{
if (va || needsparam)
return false;
Expand All @@ -4576,6 +4555,8 @@ static bool uses_specsig(jl_value_t *sig, jl_value_t *rettype, bool needsparam,
if (jl_nparams(sig) == 0)
return false;
// not invalid, consider if specialized signature is worthwhile
if (prefer_specsig)
return true;
if (isbits_spec(rettype, false))
return true;
if (jl_is_uniontype(rettype)) {
Expand Down Expand Up @@ -4829,7 +4810,7 @@ static std::unique_ptr<Module> emit_function(
}

jl_value_t *jlrettype = lam->rettype;
bool specsig = uses_specsig(lam->specTypes, jlrettype, needsparams, va, src);
bool specsig = uses_specsig(lam->specTypes, jlrettype, needsparams, va, src, params->prefer_specsig);
if (!specsig)
ctx.nReqArgs--; // function not part of argArray in jlcall

Expand Down
8 changes: 4 additions & 4 deletions src/jltypes.c
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,7 @@ jl_value_t *jl_memory_exception;
jl_value_t *jl_readonlymemory_exception;
union jl_typemap_t jl_cfunction_list;

jl_cgparams_t jl_default_cgparams = {1, 1, 1, 1, 1, 1, 1, {NULL, NULL, NULL}};
jl_cgparams_t jl_default_cgparams = {1, 1, 1, 1, 0, NULL, NULL, NULL};

// --- type properties and predicates ---

Expand Down Expand Up @@ -1663,9 +1663,9 @@ void jl_init_types(void)
jl_methtable_type = jl_new_uninitialized_datatype();
jl_nothing = jl_gc_permobj(0, NULL);

jl_default_cgparams.hooks.module_setup = jl_nothing;
jl_default_cgparams.hooks.module_activation = jl_nothing;
jl_default_cgparams.hooks.raise_exception = jl_nothing;
jl_default_cgparams.module_setup = jl_nothing;
jl_default_cgparams.module_activation = jl_nothing;
jl_default_cgparams.raise_exception = jl_nothing;

jl_emptysvec = (jl_svec_t*)jl_gc_permobj(sizeof(void*), jl_simplevector_type);
jl_svec_set_len_unsafe(jl_emptysvec, 0);
Expand Down
24 changes: 9 additions & 15 deletions src/julia.h
Original file line number Diff line number Diff line change
Expand Up @@ -1806,7 +1806,15 @@ typedef struct {
// codegen interface ----------------------------------------------------------

typedef struct {
// to disable a hook: set to NULL or nothing
int cached; // can the compiler use/populate the compilation cache?

int track_allocations; // can we track allocations?
int code_coverage; // can we measure coverage?
int static_alloc; // is the compiler allowed to allocate statically?
int prefer_specsig; // are specialized function signatures preferred?


// hooks

// module setup: prepare a module for code emission (data layout, DWARF version, ...)
// parameters: LLVMModuleRef as Ptr{Void}
Expand All @@ -1822,20 +1830,6 @@ typedef struct {
// parameters: LLVMBasicBlockRef as Ptr{Void}, LLVMValueRef as Ptr{Void}
// return value: none
jl_value_t *raise_exception;
} jl_cghooks_t;

typedef struct {
int cached; // can the compiler use/populate the compilation cache?

// language features (C-style integer booleans)
int runtime; // can we call into the runtime?
int exceptions; // are exceptions supported (requires runtime)?
int track_allocations; // can we track allocations (don't if disallowed)?
int code_coverage; // can we measure coverage (don't if disallowed)?
int static_alloc; // is the compiler allowed to allocate statically?
int dynamic_alloc; // is the compiler allowed to allocate dynamically (requires runtime)?

jl_cghooks_t hooks;
} jl_cgparams_t;
extern JL_DLLEXPORT jl_cgparams_t jl_default_cgparams;

Expand Down

0 comments on commit 8183c0f

Please sign in to comment.