guile-user
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Some introductory docs about C level threading


From: Ken Raeburn
Subject: Re: Some introductory docs about C level threading
Date: Thu, 10 Feb 2005 14:59:48 -0500

On Feb 10, 2005, at 07:05, Marius Vollmer wrote:
Ken Raeburn <address@hidden> writes:
I think someone might be tempted to do something like:

thread 1, on cpu 1, with guile core mutex locked:

(There is no guile core mutex.  Is it relevant to the discussion
below?)

Oh. Hm, I think I was reading a lot more into the scm_enter/leave_guile stuff than you had actually written, or remembering it wrong. I've seen code for other languages work this way (one thread at a time allowed in the interpreter and/or messing with object contents directly), and I guess I assumed too much and read too little. :-(

So, on re-reading, I take it that scm_leave_guile isn't about locking anything, it's about blocking outside of Guile, and not screwing up GC or async signals. Can GC happen between scm_leave_guile and the following scm_enter_guile call? If so, I assume scm_leave_guile records some info about where the current stack pointer is; so where does the stack scanner look for SCM values that might only exist in registers?

As for the details below, I don't think this affects much; I think the key point is that a thread *isn't* using a mutex.

(precondition: z is a pair, SCM_CAR(z) is a pair)
allocate cons cell x
fill in x.car = v1
fill in x.cdr = v2
SCM_SETCAR(z, x)

thread 2, on cpu 2, running without lock:

set t = SCM_CAR(z) # atomic, so we always get before or after, right?
read SCM_CAR(t) # should Just Work?

Yes, I had planned for this to just work...

With weak memory ordering, and no locking during this sequence in
either thread, I don't think we get any guarantee that SCM_CAR(t) will
get v1 instead of the uninitialized contents of the cons cell as
pulled off of the free list.

Yes, I now realize that at least initialization needs to have some
kind of memory synchronization after it.  Would declaring x.car and
x.cdr as volatile do it?

I don't think so. I think you need memory sync operations in each thread, and you need to ensure that thread 1 finishes its memory sync before thread 2 starts its memory sync.

Especially if it's one that cpu 2 happened to examine recently
(perhaps it ran the GC pass) and thus has it in cache. I think you
need a memory synchronization operation in each to guarantee this.

Needing to have the synch operation in all threads would be really
bad... is it really necessary?  If it is, I would get serious doubts
whether we can achieve the SCM is always valid' goal with full
concurrency.

I believe it is necessary. But that's part of why I was asking for people with significant real-world experience in this area to chime in. :-)

I'd love to have full concurrency. But correctness is IMNSHO more important, and I'm not sure we can get both, at least not with adequate performance as well.

If we can find some way to cope with initialization (perhaps GC and new storage allocation could end with memory sync operations in all threads, and all free-list objects in an initialized state with no references to other free-list objects?), and assume atomicity but not synchronization for SCM value modifications (though pair contents and other containers might have to become "volatile" for that to work), we might still be able to push synchronization around later modifications into application Scheme/C code, I'm not sure....

Ken




reply via email to

[Prev in Thread] Current Thread [Next in Thread]