Remaining threads failure with contexts

Andrew Whitworth wknight8111 at gmail.com
Sun Sep 9 13:30:01 UTC 2012


Tadzik found a problem with threads and lexicals, which exposes a
larger problem with threads. Here's shortened winxed code to
duplicate:

function main[main](var args)
{
    say("start");
    var x = 5;
    var t = new 'Task'(function() { say(x); });
    ${schedule t};
    ${wait t};
    say("done");
}

And here's the assertion failure I get when I run on a debug build:

start
src/call/context_accessors.c:283: failed assertion
'ctx->vtable->base_type == enum_class_CallContext'
Backtrace - Obtained 17 stack frames (max trace depth is 32).
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(Parrot_print_backtrace+0x2c)
[0x7f0586c5e6bc]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(Parrot_confess+0x9b)
[0x7f0586c5d04b]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(Parrot_pcc_get_lex_pad_func+0x75)
[0x7f0586c8a755]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(Parrot_sub_find_pad+0xa9)
[0x7f0586ccaac9]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(Parrot_find_lex_p_sc+0x57)
[0x7f0586c37e27]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(+0x12f78a)
[0x7f0586cba78a]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(runops_int+0xfa)
[0x7f0586cb9bfa]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(runops+0x1da)
[0x7f0586c8815a]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(Parrot_pcc_invoke_from_sig_object+0x1b4)
[0x7f0586c7f0a4]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(Parrot_ext_call+0x230)
[0x7f0586c5f380]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(+0x27dd06)
[0x7f0586e08d06]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(Parrot_pcc_invoke_from_sig_object+0x153)
[0x7f0586c7f043]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(Parrot_ext_call+0x230)
[0x7f0586c5f380]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(Parrot_cx_next_task+0x143)
[0x7f0586cc22a3]
/home/andrew/projects/parrot/blib/lib/libparrot.so.4.7.0(+0x1388bb)
[0x7f0586cc38bb]
/lib/x86_64-linux-gnu/libpthread.so.0(+0x7e9a) [0x7f05860bae9a]
/lib/x86_64-linux-gnu/libc.so.6(clone+0x6d) [0x7f05868c04bd]
Attempting to get PIR backtrace.  No guarantees.  Here goes...
current instr.: 'main' pc 20 ((file unknown):23) (test.winxed:6)
called from Sub '__PARROT_ENTRY_WINXED_main' pc 1381 (ext/winxed/driver.pir:484)
Aborted (core dumped)

The problem is conceptually very simple: For cross thread access we're
wrapping the callcontext in a Proxy PMC. However, some optimized code
in the system (specifically in src/call/context_accessors.c and
src/sub.c) assert the existence of a CallContext PMC only (not a
proxy) and perform direct data access on those PMCs. Unfortunately
those direct accesses create problems because the PMC type we've got
is a Proxy not a CallContext.

Switching over the direct accesses to use vtable calls instead of
direct accesses will tank performance. We've seen that before. I
suspect that adding in too many checks for CallContext/Proxy and
switching behaviors for those accesses will also be bad for
performance.

The lexicals problem that Tadzik found is only one small part of this
problem. Any time we've got a Proxied CallContext, we're going to run
into problems.

One solution I can think of now is to create a local clone of a
CallContext whenever we find a Proxy instead. LexPad and LexInfo
appear to work just fine when proxied so we only need a very shallow
clone. This creates a problem where modifications to the proxied
parent context will be made to the clone instead of the original. I
don't know how big a problem this is, but I suspect it will be small.

I'm out most of the afternoon so I'll have time to think about this
more. Any other ideas and suggestions are welcome.

--Andrew Whitworth


More information about the parrot-dev mailing list