On Tue, 2007-07-10 at 12:59 -0400, Sandro Magi wrote: > On 7/10/07, skaller <[EMAIL PROTECTED]> wrote:
> As long as you can continue useful computation while blocking, and you > can do so safely, then you have a good concurrency model. On blocking: it's the other way around. The current fibre executes UNTIL it blocks (or dies). Blocking is the only way to hand control over to another fibre. If a fibre deadlocks, it is removed, so fibres simply cannot deadlock. > I'm not sure > I see wow your approach is more efficient or safer than futures+event > loops (doesn't seem less efficient either). It isn't more efficient or safer because the model DOES use futures and event loops! Felix programs are run by a scheduler loop. A 'thread' is just a continuation. There's a list of them. The scheduler pops the top one off the list and runs it until it yields with a service request or dies. The scheduler then executes the service request. For channel I/O: if the channel is ready to be read/written, then a pointer is moved and the current thread and the one blocked on the channel are both rescheduled. [goto start] If the channel is not ready for the I/O, then the current thread is pushed onto the channels wait list. [goto start] Notice .. the thread has disappeared! The scheduler has forgotten it! It is now owned by the channel. And the channel is owned by some other active thread on the scheduler list, directly, or indirectly (via other channels and threads). If this is NOT the case .. the I/O request could never be serviced and the fact the thread is forgotten is just right .. it's unreachable so the garbage collector simply deletes it. That's IT! For synchronous scheduling. It's a master list of active fibres, plus channels with lists of fibres waiting on some other fibre to write (or read) on them. The C++ code that does all this is more or less trivial. Context switching consists of popping a pointer off a list, and calling p=p->resume() on it -- one list pop, and one virtual function dispatch. Checking if a channel is ready amounts to checking if its list of blocked readers (or writers) is a NULL pointer. Channel transfer consists of popping one fibre off the channel list and pushing it onto the master scheduler list. In other words .. the operations are all a couple of lines of very basic C code. Felix can context switch well in excess of a million threads in 2 seconds on my AMD64. So far I covered only synchronous threading. Async events work by the service holding onto the fthread pointer until the request -- eg a socket read -- has been completed, then queues the fthread into a ready queue. This async ready queue is only consulted when all the synchronous threads have died. At that time, a thread is popped off the async queue and pushed onto the sync queue. This is more expensive because the async queue interfaces pthreads and so the queue object has mutual exclusion locking. All the operations which block the OS, such as socket I/O, are handled by forwarding the requests to a server in this manner. We have two standard servers: demux (for sockets etc) and a timer thread. At this point we do not have servers for: (a) SCARY ... Unix signals :) (b) Interprocess Communication (c) other stuff, eg Windowing systems .. > So what you want is functional reactive programming (FRP), which > provides such dynamic circuit switching. You should definitely look > into it if you haven't already. I have, but my stuff was in the works long before FRP was invented, so they're just re-inventing my wheel .. :) > What you describe, basic primitive > values and combinators to wire circuits, is essentially a dataflow > graph as built using FRP signals/events + combinators. However, there > are concurrency dangers in executing this graph naively. See FrTime > [1] for details. These are the exact same concurrency problems that > event loops in E solve. With synchronous threads there are no dangers, other than the usual problem of making a mess of your code :) I've done that.. it's quite easy to forget to plug a channel in, so that when a fibre reads it it suicides .. that may be unexpected but it is well defined behaviour. With asynchronous threads (pre-emptive threads) there are definitely issues .. but whilst Felix DOES provide the programmer with pre-emptive threading as well as the synchronous threading, the emphasis is on not needing this stuff: the async I/O system interfaces to the sync I/O system seamlessly. Still, once you add the async I/O into the picture lockups are possible -- and this is entirely unavoidable when you're reliant on external event sources. > A 'vat' is pretty much the 'process' abstraction, which I think you'd > agree is fairly important and well-founded. No, it is only half a system, so it is meaningless. It is only when you specify a way processes communicate that you have an actual model. > The vat is the unit of > concurrency, failure, persistence and resource control. E also > enforces the property that each 'process' has a single event loop by > which all computation is driven, and this+persistence turns a process > into an E vat. Right. But I still don't know what that achieves .. or how it is different from Felix. Every Felix 'pthread' has its own event loop too: spawn_pthread { .... }; actually spawns a complete new synchronous scheduler with its own async queue as well. [And until recently it also spawned its own socket and timer server which was a really bad idea .. that's fixed now] This isn't a process because these threads still share memory and a single garbage collector. However there are channels for them too, pchannels. Which are a mutex locked synchronisation primitive. Major difference here is that pthreads don't get deleted by the operating system when they deadlock .. they're usually only reaped when the main process terminates. -- John Skaller <skaller at users dot sf dot net> Felix, successor to C++: http://felix.sf.net ------------------------------------------------------------------------- This SF.net email is sponsored by DB2 Express Download DB2 Express C - the FREE version of DB2 express and take control of your XML. No limits. Just data. Click to get it now. http://sourceforge.net/powerbar/db2/ _______________________________________________ Felix-language mailing list Felix-language@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/felix-language