This file describes in little detail the modifications to the
Objective-C runtime needed to make it thread safe. 

First off, kudos to Galen Hunt who is the author of this great work.

If you have an comments or just want to know where to
send me money to express your undying graditude for threading the
Objective-C runtime you can reach Galen at:

	gchunt@cs.rochester.edu

Any questions, comments, bug reports, etc. should send email either to the
GCC bug account or to:

	Scott Christley <scottc@net-community.com>

* Sarray Threading:

The most critical component of the Objective-C runtime is the sparse array
structure (sarray).  Sarrays store object selectors and implementations.  
Following in the tradition of the Objective-C runtime, my threading
support assumes that fast message dispatching is far more important
than *ANY* and *ALL* other operations.  The message dispatching thus
uses *NO* locks on any kind.  In fact, if you look in sarray.h, you
will notice that the message dispatching has not been modified.
Instead, I have modified the sarray management functions so that all
updates to the sarray data structure can be made in parallel will
message dispatching.  

To support concurrent message dispatching, no dynamically allocated
sarray data structures are freed while more than one thread is
operational.  Sarray data structures that are no longer in use are
kept in a linked list of garbage and are released whenever the program
is operating with a single thread.  The programmer can also flush the 
garbage list by calling sarray_remove_garbage when the programmer can
ensure that no message dispatching is taking place concurrently.  The
amount of un-reclaimed sarray garbage should normally be extremely
small in a real program as sarray structures are freed only when using
the "poseAs" functionality and early in program initialization, which
normally occurs while the program is single threaded.

******************************************************************************
* Static Variables:

The following variables are either statically or globally defined. This list 
does not include variables which are internal to implementation dependent 
versions of thread-*.c.

The following threading designations are used:
	SAFE   : Implicitly thread safe.
	SINGLE : Must only be used in single thread mode.
	MUTEX  : Protected by single global mutex objc_runtime_mutex.
	UNUSED : Not used in the runtime.

Variable Name:			Usage:  Defined:	Also used in:
===========================	======	============	=====================
__objc_class_hash		MUTEX	class.c
__objc_class_links_resolved	UNUSED	class.c		runtime.h
__objc_class_number		MUTEX	class.c
__objc_dangling_categories	UNUSED	init.c
__objc_module_list		MUTEX	init.c
__objc_selector_array		MUTEX	selector.c
__objc_selector_hash		MUTEX	selector.c
__objc_selector_max_index	MUTEX	selector.c	sendmsg.c runtime.h
__objc_selector_names		MUTEX	selector.c
__objc_thread_exit_status	SAFE	thread.c
__objc_uninstalled_dtable	MUTEX	sendmsg.c	selector.c
_objc_load_callback		SAFE	init.c		objc-api.h
_objc_lookup_class		SAFE	class.c		objc-api.h
_objc_object_alloc		SINGLE	objects.c	objc-api.h
_objc_object_copy		SINGLE	objects.c	objc-api.h
_objc_object_dispose		SINGLE	objects.c	objc-api.h
frwd_sel			SAFE2	sendmsg.c
idxsize				MUTEX	sarray.c	sendmsg.c sarray.h
initialize_sel			SAFE2	sendmsg.c
narrays				MUTEX	sarray.c	sendmsg.c sarray.h
nbuckets			MUTEX	sarray.c	sendmsg.c sarray.h
nindices			MUTEX	sarray.c	sarray.h
previous_constructors		SAFE1	init.c
proto_class			SAFE1	init.c
unclaimed_categories		MUTEX	init.c
unclaimed_proto_list		MUTEX	init.c
uninitialized_statics		MUTEX	init.c

Notes:
1) Initialized once in unithread mode.
2) Initialized value will always be same, guaranteed by lock on selector 
   hash table.


******************************************************************************
* Frontend/Backend design:

The design of the Objective-C runtime thread and mutex functions utilizes a
frontend/backend implementation.

The frontend, as characterized by the files thr.h and thr.c, is a set
of platform independent structures and functions which represent the
user interface.  Objective-C programs should use these structures and
functions for their thread and mutex work if they wish to maintain a
high degree of portability across platforms.

The backend is composed of a file with the necessary code to map the ObjC
thread and mutex to a platform specific implementation.  For example, the
file thr-solaris.c contains the implementation for Solaris.  When you 
configure GCC, it attempts to pick an appropriate backend file for the
target platform; however, you can override this choice by assign the
OBJC_THREAD_FILE make variable to the basename of the backend file.  This
is especially useful on platforms which have multiple thread libraries.
For example:

	make OBJC_THREAD_FILE=thr-posix

would indicate that the generic posix backend file, thr-posix.c, should be
compiled with the ObjC runtime library.  If your platform does not support
threads then you should specify the OBJC_THREAD_FILE=thr-single backend file
to compile the ObjC runtime library without thread or mutex support; note
that programs which rely upon the ObjC thread and mutex functions will
compile and link correctly but attempting to create a thread or mutex will
result in an error.

It is questionable whether it is really necessary to have both a
frontend and backend function for all available functionality.  On the
one hand, it provides a clear, consistent differentiation between what
is public and what is private with the downside of having the overhead
of multiple functions calls.  For example, the function to have a thread
yield the processor is objc_thread_yield; in the current implementation
this produces a function call set:

objc_thread_yield()  ->  __objc_thread_yield()  ->  system yield function

This has two extra function calls over calling the platform specific function
explicitly, but the issue is whether only the overhead of a single function
is necessary.

objc_thread_yield()  ->  system yield function

This breaks the public/private dichotomy between the frontend/backend
for the sake of efficiency.  It is possible to just use a preprocessor
define so as to eliminate the extra function call:

#define objc_thread_yield() __objc_thread_yield()

This has the undesirable effect that if objc_thread_yield is actually
turned into a function based upon future need; then ObjC programs which
access the thread functions would need to be recompiled versus just
being relinked.
 
******************************************************************************
* Threads:

The thread system attempts to create multiple threads using whatever
operating system or library thread support is available.  It does
assume that all system functions are thread safe.  Notably this means
that the system implementation of malloc and free must be thread safe.
If a system has multiple processors, the threads are configured for
full parallel processing.

* Backend initialization functions

__objc_init_thread_system(void), int
	Initialize the thread subsystem.  Called once by __objc_exec_class.
	Return -1 if error otherwise return 0.

__objc_close_thread_system(void), int
	Closes the thread subsystem, not currently guaranteed to be called.
	Return -1 if error otherwise return 0.

*****
* Frontend thread functions
* User programs should use these functions.

objc_thread_detach(SEL selector, id object, id argument), objc_thread_t
	Creates and detaches a new thread.  The new thread starts by
	sending the given selector with a single argument to the
	given object.

objc_thread_set_priority(int priority), int
	Sets a thread's relative priority within the program.  Valid
	options are:
	
	OBJC_THREAD_INTERACTIVE_PRIORITY
	OBJC_THREAD_BACKGROUND_PRIORITY
	OBJC_THREAD_LOW_PRIORITY

objc_thread_get_priority(void), int
	Query a thread's priority.

objc_thread_yield(void), void
	Yields processor to another thread with equal or higher
	priority.  It is up to the system scheduler to determine if
	the processor is taken or not.

objc_thread_exit(void), int
	Terminates a thread.  If this is the last thread executing
	then the program will terminate.

objc_thread_id(void), int
	Returns the current thread's id.

objc_thread_set_data(void *value), int
	Set a pointer to the thread's local storage.  Local storage is
	thread specific.

objc_thread_get_data(void), void *
	Returns the pointer to the thread's local storage.

*****
* Backend thread functions
* User programs should *NOT* directly call these functions.

__objc_thread_detach(void (*func)(void *arg), void *arg), objc_thread_t
	Spawns a new thread executing func, called by objc_thread_detach.
	Return NULL if error otherwise return thread id.

__objc_thread_set_priority(int priority), int
	Set the thread's priority, called by objc_thread_set_priority.
	Return -1 if error otherwise return 0.

__objc_thread_get_priority(void), int
	Query a thread's priority, called by objc_thread_get_priority.
	Return -1 if error otherwise return the priority.

__objc_thread_yield(void), void
	Yields the processor, called by objc_thread_yield.

__objc_thread_exit(void), int
	Terminates the thread, called by objc_thread_exit.
	Return -1 if error otherwise function does not return.

__objc_thread_id(void), objc_thread_t
	Returns the current thread's id, called by objc_thread_id.
	Return -1 if error otherwise return thread id.

__objc_thread_set_data(void *value), int
	Set pointer for thread local storage, called by objc_thread_set_data.
	Returns -1 if error otherwise return 0.

__objc_thread_get_data(void), void *
	Returns the pointer to the thread's local storage.
	Returns NULL if error, called by objc_thread_get_data.


******************************************************************************
* Mutexs:

Mutexs can be locked recursively.  Each locked mutex remembers
its owner (by thread id) and how many times it has been locked.  The
last unlock on a mutex removes the system lock and allows other
threads to access the mutex.

*****
* Frontend mutex functions
* User programs should use these functions.

objc_mutex_allocate(void), objc_mutex_t
	Allocates a new mutex.  Mutex is initially unlocked.
	Return NULL if error otherwise return mutex pointer.

objc_mutex_deallocate(objc_mutex_t mutex), int
	Free a mutex.  Before freeing the mutex, makes sure that no
	one else is using it.
	Return -1 if error otherwise return 0.

objc_mutex_lock(objc_mutex_t mutex), int
	Locks a mutex.  As mentioned earlier, the same thread may call
	this routine repeatedly.
	Return -1 if error otherwise return 0.
	
objc_mutex_trylock(objc_mutex_t mutex), int
	Attempts to lock a mutex.  If lock on mutex can be acquired 
	then function operates exactly as objc_mutex_lock.
	Return -1 if failed to acquire lock otherwise return 0.

objc_mutex_unlock(objc_mutex_t mutex), int
	Unlocks the mutex by one level.  Other threads may not acquire
	the mutex until this thread has released all locks on it.
	Return -1 if error otherwise return 0.

*****
* Backend mutex functions
* User programs should *NOT* directly call these functions.

__objc_mutex_allocate(objc_mutex_t mutex), int
	Allocates a new mutex, called by objc_mutex_allocate.
	Return -1 if error otherwise return 0.

__objc_mutex_deallocate(objc_mutex_t mutex), int
	Free a mutex, called by objc_mutex_deallocate.
	Return -1 if error otherwise return 0.

__objc_mutex_lock(objc_mutex_t mutex), int
	Locks a mutex, called by objc_mutex_lock.
	Return -1 if error otherwise return 0.
	
__objc_mutex_trylock(objc_mutex_t mutex), int
	Attempts to lock a mutex, called by objc_mutex_trylock.
	Return -1 if failed to acquire lock or error otherwise return 0.

__objc_mutex_unlock(objc_mutex_t mutex), int
	Unlocks the mutex, called by objc_mutex_unlock.
	Return -1 if error otherwise return 0.

******************************************************************************
* Condition Mutexs:

Mutexs can be locked recursively.  Each locked mutex remembers
its owner (by thread id) and how many times it has been locked.  The
last unlock on a mutex removes the system lock and allows other
threads to access the mutex.

*
* Frontend condition mutex functions
* User programs should use these functions.
*

objc_condition_allocate(void), objc_condition_t 
	Allocate a condition mutex.
	Return NULL if error otherwise return condition pointer.

objc_condition_deallocate(objc_condition_t condition), int
	Deallocate a condition. Note that this includes an implicit
	condition_broadcast to insure that waiting threads have the 
	opportunity to wake.  It is legal to dealloc a condition only
	if no other thread is/will be using it. Does NOT check for
	other threads waiting but just wakes them up.
	Return -1 if error otherwise return 0.

objc_condition_wait(objc_condition_t condition, objc_mutex_t mutex), int
	Wait on the condition unlocking the mutex until objc_condition_signal()
	or objc_condition_broadcast() are called for the same condition. The
	given mutex *must* have the depth 1 so that it can be unlocked
	here, for someone else can lock it and signal/broadcast the condition.
	The mutex is used to lock access to the shared data that make up the
	"condition" predicate.
	Return -1 if error otherwise return 0.
	
objc_condition_broadcast(objc_condition_t condition), int
	Wake up all threads waiting on this condition. It is recommended that 
	the called would lock the same mutex as the threads in
	objc_condition_wait before changing the "condition predicate"
	and make this call and unlock it right away after this call.
	Return -1 if error otherwise return 0.

objc_condition_signal(objc_condition_t condition), int
	Wake up one thread waiting on this condition.
	Return -1 if error otherwise return 0.

*
* Backend condition mutex functions
* User programs should *NOT* directly call these functions.
*

__objc_condition_allocate(objc_condition_t condition), int
	Allocate a condition mutex, called by objc_condition_allocate.
	Return -1 if error otherwise return 0.

__objc_condition_deallocate(objc_condition_t condition), int
	Deallocate a condition, called by objc_condition_deallocate.
	Return -1 if error otherwise return 0.

__objc_condition_wait(objc_condition_t condition, objc_mutex_t mutex), int
	Wait on the condition, called by objc_condition_wait.
	Return -1 if error otherwise return 0 when condition is met.
	
__objc_condition_broadcast(objc_condition_t condition), int
	Wake up all threads waiting on this condition.
	Called by objc_condition_broadcast.
	Return -1 if error otherwise return 0.

__objc_condition_signal(objc_condition_t condition), int
	Wake up one thread waiting on this condition.
	Called by objc_condition_signal.
	Return -1 if error otherwise return 0.
