On 8/26/14 4:25 PM, Cameron Zwarich wrote:
Cons: - Still requires an abstraction layer for features that differ across platforms, unless we fix a target platform. - There is a semantic gap between OS I/O primitives and Rust channels, and the problem of having a task that processes events from both still needs to be solved. - It is not easy to reclaim the wasted stack space of native threads. - We currently have a lot of per-pipeline tasks for loading resources, caches, etc. If we used native threads, it seems unlikely that we would use individual threads for each of these (e.g. every single loader task for every frame doing independent multiplexing of I/O), and we would want to pool them across pipelines. This introduces the (fairly certain, given past experiences) risk of Rust task failure induced by one pipeline affecting the loading of resources for another pipeline. Building on a smaller browser-agnostic abstraction means that the amount of trusted code (for the sake of isolation, not mere memory safety) is reduced, and there is less of a chance of browser-specific concerns causing problems.
Your email deserves a more thought-out response than this, so I owe a more in-depth reply, but just for what it's worth: I think the "failure brings down other unrelated I/O operations in the thread pool" is an important point that we will need to address. Indeed, "use a native task per I/O resource so that we can handle failure" isn't a very compelling story.
Part of the solution may well be to isolate failure using the "evil" `try` functionality in the standard library. To be clear, I don't imagine this will entail full C++/Java-style exceptions: there would be a sharing limitation (which can be enforced by bounds on a callback) to encourage construction of data structures that are safe for error recovery.
In a sense, using `try` in this way is forcing us to recreate part of libgreen. However, in the context of the resource manager, I think it's better for Servo than libgreen was from an efficiency standpoint. This is because the `try` model decouples two things that libgreen forced clients to glue together: *failure isolation* and *a machine stack*. In the libgreen model, if you want to isolate failure (which is very much desired by Servo), you need to keep a machine stack around in 1:1 correspondence with your failure domain (which does not seem desirable for each I/O resource from a memory usage point of view). For I/O resources, there's no need to keep a machine stack around, as the amount of state that each I/O resource needs can be significantly smaller than an entire machine stack. (High-performance evented I/O servers like nginx and HAProxy demonstrate that the performance gains of forgoing the machine stack can be significant.)
There's definitely work to be done to create all of this functionality, but I think that there's a reasonable case to be made that, as far as the performance of the resource task is concerned, Servo will come out better than it would have using libgreen.
Patrick _______________________________________________ dev-servo mailing list dev-servo@lists.mozilla.org https://lists.mozilla.org/listinfo/dev-servo