You are currently viewing a snapshot of www.mozilla.org taken on April 21, 2008. Most of this content is highly out of date (some pages haven't been updated since the project began in 1998) and exists for historical purposes only. If there are any pages on this archive site that you think should be added back to www.mozilla.org, please file a bug.



Multithreading in Necko
Darin Fisher <darin at meer dot net>
December 10, 2001

Overview

Necko's primary interfaces are NOT thread safe. There has not yet been a need to make Necko entirely thread safe as most of Mozilla (and especially most of Gecko) run only on the main/primordial thread. In the future, Necko may be made thread safe to support changes to Gecko that would put some other processing work on background threads (eg. multithreaded image decoding).

However, most Necko protocols utilize background threads. Background threads are used to manage all I/O operations (with the exception of few cases).

Most simple protocol handlers (eg. file, finger, datetime) do not worry about threading issues. The internal I/O interfaces default to proxying all callbacks to the main thread. This keeps simple protocol handlers simple :-)

More complex protocol handlers (eg. http, ftp) operate partially on the background threads to improve performance. For example, the http protocol handler has code that runs on the socket transport thread to kick off pending requests well before the main thread would get around to doing so.

Socket Transport Thread (1)

Socket connections are processed on a single background thread. This thread is controlled by the nsSocketTransportService. It sits in a loop, polling a list of sockets. When a socket can be read, the socket's listener is notified either synchronously (on the same thread) or asynchronously via a nsIStreamListenerProxy impl.

File Transport Threads (1-4)

File I/O is processed via a thread pool that has between 1 and 4 threads. These threads are controlled by the nsFileTransportService. Each file transport object is given time on one of the file transport threads. During which it reads (writes) until its buffers are full (empty). Once at the limit of its buffers, it yields the thread to another pending file transport object.

As with the socket transport thread, the nsIStreamListener passed to a file transport's AsyncRead method can operate partially on the file transport's thread before proxying data to the main thread.

The file transport is confusingly named since it is not restricted to loading files. It simply promises to read from a nsIInputStream (or write to a nsIOutputStream) on a background thread. The implementation of the stream should be blocking; however, there is limited support for non-blocking streams.

Cached page loads, file URL loads, and jar URL loads all utilize the file transport service. The jar protocol handler, for rexample, passes a special nsIInputStream impl that does gzip decoding on the fly.

DNS Thread (0-1)

On most platforms DNS requests a processed on a background thread. However, the details of the implementation are heavily platform dependent. For example, on XP_WIN an invisible window is created with a message pump on a background thread for processing WSA asynchronous DNS events. In this way, Necko takes advantage of the platforms specific routines for DNS lookups. The default implementation does not spawn a worker thread, and instead simply calls PR_GetIPNodeByName (essentially equivalent to gethostbyname).