---------------------------Thread/Process abstraction

NOTE:  There is a one-to-one mapping between process and process_attr's.  This
       relationship does not exist with threads and thread_attr's.

 ap_int32_t ap_fork(ap_proc_t *)
        create a new process with a copy of the currently executing address space.
     Arguments:
        arg 1)  the proccess type for the newly created process.  NULL on error.
                which fields are filled out in this structure is undefined.
        return) status.  -1 on error, 0 if child process, 1 if original
                process.
NOTE:  This is a non-portable call.  It cannot be avoided, and any system that 
       can create this function should do so.  Any platform that is not able
       to produce this function should define it as NULL, so that there are
       no compile time errors. 
        
 ap_procattr_t *ap_createprocattr_init(void);
        create a new process attr type with OS dependant defaults
     Arguments:
        return) New process attribute type.

 ap_status_t ap_setprocattr_io(ap_procattr_t *, ap_int32_t, ap_int32_t, ap_int32_t)
        setup stdin, stdout, and stderr attributes for the new proc
     Arguments
        arg 1)  the process attr to modify
        arg 2)  Should we setup a pipe for stdin? 1 yes, 0 no. 
        arg 3)  Should we setup a pipe for stdout? 1 yes, 0 no
        arg 4)  Should we setup a pipe for stderr? 1 yes, 0 no.
        return) APR_SUCCESS or APR_FAILURE
NOTE:  the file structures are a part of the process attr variable.  They are
       created and filled out by this func.  On UNIX, this function actually
       creates the pipe(s), but lets ap_create_process set them up as 
       std(in|out|err).

 ap_status_t ap_setprocattr_dir(ap_procattr_t *, char *)
       define starting directory for new process.
     Arguments
       arg 1)  The process attr to modify
       arg 2)  The starting directory for the new process.
       return) APR_SUCCESS or APR_FAILURE

 ap_proc_t *ap_create_process(char *, char *const [], char **, const ap_procattr_t *)
	create a new process and run a new executable in it.
     Arguments:
	arg 1)  Path name of the executable file 
	arg 2)  array of command line arguments.  The first string in the array
                should be the program name to execute.
	arg 3)  array of environment strings of the form name=value.
		If NULL, inherit environ from parent.
	arg 4)  a pointer to structure that describes the attributes of the new
		process.  If NULL, process will have the default attributes.
	return) Process description structure.  NULL on failure

 ap_file_t *ap_get_childin(ap_proc_t *)
        Get the parent side of the pipe that connects to the child's stdin.
        This function is only valid after a process has successfully spawned
        a child
     Arguments:
        arg 1)  The process that spawned the child
        return) The file to use when writing to the child's stdin.  NULL
                on error. 

 ap_file_t *ap_get_childout(ap_proc_t *)
        Get the parent side of the pipe that connects to the child's stdout.
        This function is only valid after a process has successfully spawned
        a child
     Arguments:
        arg 1)  The process that spawned the child
        return) The file to use when reading from the child's stdout.  NULL
                on error. 

 ap_file_t *ap_get_childerr(ap_proc_t *)
        Get the parent side of the pipe that connects to the child's stderr.
        This function is only valid after a process has successfully spawned
        a child
     Arguments:
        arg 1)  The process that spawned the child
        return) The file to use when reading from the child's stderr.  NULL
                on error.   

 ap_status_t ap_wait_proc(ap_proc_t *, ap_wait_how_e) 
        Wait for a specified process to exit
     Arguments:
        arg 1)  The process to wait for.
        arg 2)  wait for a process to die, or return immediately
                APR_WAIT
                APR_NOWAIT
        return) APR_SUCCESS or APR_fAILURE

 ap_threadattr_t *ap_create_threadattr(ap_context_t *);
        create a new thread attr type with OS dependant defaults
     Arguments:
        arg 1)  The context to operate on. 
        return) New thread attribute type.
NOTE:  All threads should be started joinable by default.

ap_status_t ap_setthreadattr_detach(ap_context_t *, ap_threadattr_t *, ap_int32_t)
        Determine if a thread is joinable or detached when created.
     Arguments:
        arg 1)  The context to operate on.
        arg 2)  The attribute to modify
        arg 3)  1 -> start detached, 0 -> start joinable.
        return) APR_SUCCESS or APR_FAILURE

ap_status_t ap_getthreadattr_detach(ap_context_t *, ap_threadattr_t *)
        Question thread if is joinable or detached when created.
     Arguments:
        arg 1)  The context to operate on.
        arg 2)  The attribute to modify
        return) APR_SUCCESS if detached or APR_FAILURE if joinable.

 ap_thread_t *ap_create_thread(ap_context_t *, ap_threadattr_t *, void * (void *), void *)
	Create a new thread
     Arguments:
        arg 1)  The context to operate on
        arg 2)  The attributes to use when creating the thread.
	arg 3)	pointer to the root function of the new thread.  This function
		is called when the thread is created.  Returning from this
		function is the only way to terminate the thread.
	arg 4)	parameter to pass to thread's root func.
	return) The thread created.

 ap_status_t ap_cancel_thread(ap_context_t *, ap_thread_t *)
        Cancel the specified thread
     Arguments:
        arg 1)  The context to operate on.
        arg 2)  The thread to be canceled.
        return) APR_SUCCESS or APR_FAILURE. 
NOTE:  The return doesn't determine if the thread has been canceled or not.  The
       thread itself can determine if it should ignore, honor, or defer the
       request to die.  The return code only determines if the request was
       sent properly.

 ap_status_t ap_set_canceltype(ap_context_t *, ap_int32_t)
        How do I cancel this thread?
     Arguments:
        arg 1)  The context to operate on.
        arg 2)  How to cancel a thread.  One of:
                   APR_CANCEL_ASYNCH
                   APR_CANCEL_DEFER
        return) APR_SUCCESS or APR_FAILURE
NOTE:  This function works on the current thread only.

 ap_status_t ap_set_cancelstate(ap_context_t *, ap_int32_t)
        Can I cancel this thread?
     Arguments:
        arg 1)  The context to operate on.
        arg 2)  Can I cancel this thread.  One of:
                   APR_CANCEL_ENABLE
                   APR_CANCEL_DISABLE
        return) APR_SUCCESS or APR_FAILURE
NOTE:  This function works on the current thread only.

 void ap_thread_exit(ap_context_t *, ap_status_t *)
        Exit this therad immediately.
     Arguments:
        arg 1)  The context to operate on.
        arg 2)  The value to return when the thread exits.  Either APR_SUCCESS
                of APR_FAILURE.  NULL is also valid here.
        return) This function NEVER returns.

 ap_status_t ap_thread_join(ap_context_t *, ap_thread_t *, ap_status_t *)
        Wait for specified thread to exit.
     Arguments:
        arg 1)  The context to operate on.
        arg 2)  The thread to wait for.
        arg 3)  The return value of the thread we are waiting for.
        return) APR_SUCCESS or APR_FAILURE.

 ap_status_t ap_thread_detach(ap_context_t *, ap_thread_t *)
        Mark a thread as being detached.  No longer a need to join on it.
     Arguments:
        arg 1)  Context to operate on.
        arg 2)  Thread to mark as detached.
        return) APR_SUCCESS or APR_FAILURE

 ap_key_t ap_create_thread_private(ap_context_t *, void (*dest)(void *))
	create per-thread private data.
     Arguments:
	arg 1)  context to operate on.
	arg 2)  function used to destroy private data. 
        return) Platform dependant key to retrieve private data.

 ap_status_t ap_set_thread_private(ap_context_t *, ap_key_t, void *)
        Set the thread private data for the current thread
     Arguments:
	arg 1)  Context to operate on. 
	arg 2)  Key to thread's private data.
        arg 3)  Data to set as thread private.
        return) a pointer to the private data.



**************** IMPLEMENTATION DETAILS **************   

