Commit f834dfdc authored by Kevin Modzelewski's avatar Kevin Modzelewski

Try to reduce cxx-exception-fixup overhead

I think this is the main source of our jit-time regression.
parent dceb1e9e
......@@ -373,20 +373,25 @@ void addCXXFixup(llvm::Instruction* inst, const llvm::SmallVector<llvm::Tracking
call->replaceAllUsesWith(new_invoke);
call->eraseFromParent();
llvm::Value* exc_type, *exc_value, *exc_traceback;
std::tie(exc_type, exc_value, exc_traceback) = createLandingpad(fixup_block);
llvm::IRBuilder<true> builder(fixup_block);
llvm::SmallVector<llvm::Value*, 4> decref_args;
decref_args.push_back(getConstantInt(to_decref.size(), g.i32));
decref_args.append(to_decref.begin(), to_decref.end());
builder.CreateCall(g.funcs.xdecrefAll, decref_args);
auto rethrow = builder.CreateCall3(g.funcs.rawReraise, exc_type, exc_value, exc_traceback);
static llvm::Function* _personality_func = g.stdlib_module->getFunction("__gxx_personality_v0");
assert(_personality_func);
llvm::Value* personality_func
= g.cur_module->getOrInsertFunction(_personality_func->getName(), _personality_func->getFunctionType());
assert(personality_func);
static llvm::Type* lp_type = llvm::StructType::create(std::vector<llvm::Type*>{ g.i8_ptr, g.i64 });
assert(lp_type);
llvm::LandingPadInst* landing_pad = builder.CreateLandingPad(lp_type, personality_func, 1);
landing_pad->addClause(getNullPtr(g.i8_ptr));
llvm::SmallVector<llvm::Value*, 4> call_args;
llvm::Value* cxaexc_pointer = builder.CreateExtractValue(landing_pad, { 0 });
call_args.push_back(cxaexc_pointer);
call_args.push_back(getConstantInt(to_decref.size(), g.i32));
call_args.append(to_decref.begin(), to_decref.end());
builder.CreateCall(g.funcs.xdecrefAndRethrow, call_args);
builder.CreateUnreachable();
// new_invoke->getParent()->getParent()->dump();
}
// TODO: this should be cleaned up and moved to src/core/
......
......@@ -324,7 +324,7 @@ void initGlobalFuncs(GlobalState& g) {
GET(reraiseCapiExcAsCxx);
GET(deopt);
GET(checkRefs);
GET(xdecrefAll);
GET(xdecrefAndRethrow);
GET(div_float_float);
GET(floordiv_float_float);
......
......@@ -55,7 +55,7 @@ struct GlobalFuncs {
llvm::Value* raise0, *raise0_capi, *raise3, *raise3_capi, *rawReraise;
llvm::Value* PyErr_Fetch, *PyErr_NormalizeException, *PyErr_Restore, *caughtCapiException, *reraiseCapiExcAsCxx;
llvm::Value* deopt;
llvm::Value* checkRefs, *xdecrefAll;
llvm::Value* checkRefs, *xdecrefAndRethrow;
llvm::Value* div_float_float, *floordiv_float_float, *mod_float_float, *pow_float_float;
......
......@@ -140,7 +140,7 @@ void force() {
FORCE(reraiseCapiExcAsCxx);
FORCE(deopt);
FORCE(checkRefs);
FORCE(xdecrefAll);
FORCE(xdecrefAndRethrow);
FORCE(div_i64_i64);
FORCE(mod_i64_i64);
......
......@@ -118,7 +118,10 @@ static inline Box* callattrInternal3(Box* obj, BoxedString* attr, LookupScope sc
return callattrInternal<S, rewritable>(obj, attr, scope, rewrite_args, argspec, arg1, arg2, arg3, NULL, NULL);
}
extern "C" void xdecrefAll(int num, ...) {
extern "C" void* __cxa_begin_catch(void*);
extern "C" void xdecrefAndRethrow(void* cxa_ptr, int num, ...) {
ExcInfo e = *(ExcInfo*)__cxa_begin_catch(cxa_ptr);
va_list va;
va_start(va, num);
......@@ -128,6 +131,8 @@ extern "C" void xdecrefAll(int num, ...) {
}
va_end(va);
rawReraise(e.type, e.value, e.traceback);
}
extern "C" Box* deopt(AST_expr* expr, Box* value) {
......
......@@ -231,6 +231,6 @@ extern "C" void boxedLocalsDel(Box* boxedLocals, BoxedString* attr);
extern "C" void checkRefs(Box* b); // asserts that b has >= 0 refs
extern "C" Box* assertAlive(Box* b); // asserts that b has > 0 refs, and returns b
extern "C" void xdecrefAll(int num, ...);
extern "C" void xdecrefAndRethrow(void* cxa_ptr, int num_decref, ...);
}
#endif
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment