You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@apr.apache.org by rb...@apache.org on 2001/09/18 23:38:03 UTC

cvs commit: apr/locks/win32 thread_cond.c

rbb         01/09/18 14:38:03

  Modified:    include/arch/win32 thread_cond.h
               locks/win32 thread_cond.c
  Log:
  An initial thread_condition variable implementation for Windows.
  This is kind of ugly, but I believe it works.  It does pass all of
  the APR tests, and I don't see any race conditions, but other
  eyes are more than welcome on this code now.
  
  Revision  Changes    Path
  1.2       +5 -0      apr/include/arch/win32/thread_cond.h
  
  Index: thread_cond.h
  ===================================================================
  RCS file: /home/cvs/apr/include/arch/win32/thread_cond.h,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- thread_cond.h	2001/09/13 01:04:23	1.1
  +++ thread_cond.h	2001/09/18 21:38:03	1.2
  @@ -59,6 +59,11 @@
   
   struct apr_thread_cond_t {
       apr_pool_t *pool;
  +    HANDLE event;
  +    HANDLE mutex;
  +    int signal_all;
  +    int num_waiting;
  +    int signalled;
   };
   
   #endif  /* THREAD_COND_H */
  
  
  
  1.2       +68 -5     apr/locks/win32/thread_cond.c
  
  Index: thread_cond.c
  ===================================================================
  RCS file: /home/cvs/apr/locks/win32/thread_cond.c,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- thread_cond.c	2001/09/13 01:04:23	1.1
  +++ thread_cond.c	2001/09/18 21:38:03	1.2
  @@ -60,29 +60,92 @@
   #include "win32/thread_cond.h"
   #include "apr_portable.h"
   
  +static apr_status_t thread_cond_cleanup(void *data)
  +{
  +    apr_thread_cond_t *cond = data;
  +    if (cond->num_waiting != 0) {
  +        printf("somebody's waiting, but I'm closing it anyway.\n");
  +    }
  +    CloseHandle(cond->mutex);
  +    CloseHandle(cond->event);
  +    return APR_SUCCESS;
  +}
  +
   APR_DECLARE(apr_status_t) apr_thread_cond_create(apr_thread_cond_t **cond,
                                                    apr_pool_t *pool)
   {
  -    return APR_ENOTIMPL;
  +    *cond = apr_palloc(pool, sizeof(**cond));
  +    (*cond)->pool = pool;
  +    (*cond)->event = CreateEvent(NULL, TRUE, FALSE, NULL);
  +    (*cond)->mutex = CreateMutex(NULL, FALSE, NULL);
  +    (*cond)->signal_all = 0;
  +    (*cond)->num_waiting = 0;
  +    return APR_SUCCESS;
   }
   
   APR_DECLARE(apr_status_t) apr_thread_cond_wait(apr_thread_cond_t *cond,
                                                  apr_thread_mutex_t *mutex)
   {
  -    return APR_ENOTIMPL;
  +    DWORD rv;
  +
  +    while (1) {
  +        WaitForSingleObject(cond->mutex, INFINITE);
  +        cond->num_waiting++;
  +        ReleaseMutex(cond->mutex);
  +
  +        apr_thread_mutex_unlock(mutex);
  +        rv = WaitForSingleObject(cond->event, INFINITE);
  +        cond->num_waiting--;
  +        if (rv == WAIT_FAILED) {
  +            return apr_get_os_error();
  +        }
  +        if (cond->signal_all) {
  +            if (cond->num_waiting == 0) {
  +                ResetEvent(cond->event);
  +            }
  +            break;
  +        }
  +        if (cond->signalled) {
  +            cond->signalled = 0;
  +            ResetEvent(cond->event);
  +            break;
  +        }
  +        ReleaseMutex(cond->mutex);
  +    }
  +    apr_thread_mutex_lock(mutex);
  +    return APR_SUCCESS;
   }
   
   APR_DECLARE(apr_status_t) apr_thread_cond_signal(apr_thread_cond_t *cond)
   {
  -    return APR_ENOTIMPL;
  +    DWORD rv;
  +
  +    WaitForSingleObject(cond->mutex, INFINITE);
  +    cond->signalled = 1;
  +    rv = SetEvent(cond->event);
  +    ReleaseMutex(cond->mutex);
  +    if (rv == 0) {
  +        return apr_get_os_error();
  +    }
  +    return APR_SUCCESS;
   }
   
   APR_DECLARE(apr_status_t) apr_thread_cond_broadcast(apr_thread_cond_t *cond)
   {
  -    return APR_ENOTIMPL;
  +    DWORD rv;
  +
  +    WaitForSingleObject(cond->mutex, INFINITE);
  +    cond->signalled = 1;
  +    cond->signal_all = 1;
  +    rv = SetEvent(cond->event);
  +    ReleaseMutex(cond->mutex);
  +    if (rv == 0) {
  +        return apr_get_os_error();
  +    }
  +    return APR_SUCCESS;
   }
   
   APR_DECLARE(apr_status_t) apr_thread_cond_destroy(apr_thread_cond_t *cond)
   {
  -    return APR_ENOTIMPL;
  +    return apr_pool_cleanup_run(cond->pool, cond, thread_cond_cleanup);
   }
  
  
  

Re: cvs commit: apr/locks/win32 thread_cond.c

Posted by Greg Stein <gs...@lyra.org>.
On Tue, Sep 18, 2001 at 07:53:04PM -0700, Ian Holsman wrote:
> On Tue, 2001-09-18 at 18:03, Greg Stein wrote:
> > On Tue, Sep 18, 2001 at 09:38:03PM -0000, rbb@apache.org wrote:
>...
> > >   +static apr_status_t thread_cond_cleanup(void *data)
> > >   +{
> > >   +    apr_thread_cond_t *cond = data;
> > >   +    if (cond->num_waiting != 0) {
> > >   +        printf("somebody's waiting, but I'm closing it anyway.\n");
> > 
> > Can't have a printf() in there. Not sure what the right answer is; maybe
> > call the pool's abort function.
> 
> you >could< use the apr_file_printf function 
> and use stderr from the apr_open_stderr call.
> this gets put into the log files, the std fprintf doesnt.

That doesn't change anything. The general policy is that APR is a library,
so it shouldn't be outputing to *any* file descriptor.

Who knows what FD 2 is bound to? Only the app does. Maybe that is a binary
file it is constructing. You sure don't want to spam it with text.

Cheers,
-g

-- 
Greg Stein, http://www.lyra.org/

Re: cvs commit: apr/locks/win32 thread_cond.c

Posted by Ian Holsman <Ia...@cnet.com>.
On Tue, 2001-09-18 at 18:03, Greg Stein wrote:
> On Tue, Sep 18, 2001 at 09:38:03PM -0000, rbb@apache.org wrote:
> > rbb         01/09/18 14:38:03
> > 
> >   Modified:    include/arch/win32 thread_cond.h
> >                locks/win32 thread_cond.c
> >   Log:
> >   An initial thread_condition variable implementation for Windows.
> >   This is kind of ugly, but I believe it works.  It does pass all of
> >   the APR tests, and I don't see any race conditions, but other
> >   eyes are more than welcome on this code now.
> >...
> >   --- thread_cond.c	2001/09/13 01:04:23	1.1
> >   +++ thread_cond.c	2001/09/18 21:38:03	1.2
> >   @@ -60,29 +60,92 @@
> >    #include "win32/thread_cond.h"
> >    #include "apr_portable.h"
> >    
> >   +static apr_status_t thread_cond_cleanup(void *data)
> >   +{
> >   +    apr_thread_cond_t *cond = data;
> >   +    if (cond->num_waiting != 0) {
> >   +        printf("somebody's waiting, but I'm closing it anyway.\n");
> 
> Can't have a printf() in there. Not sure what the right answer is; maybe
> call the pool's abort function.

you >could< use the apr_file_printf function 
and use stderr from the apr_open_stderr call.
this gets put into the log files, the std fprintf doesnt.
> 
> Cheers,
> -g
> 
> -- 
> Greg Stein, http://www.lyra.org/
-- 
Ian Holsman
Performance Measurement & Analysis
CNET Networks    -    415 364-8608

Re: cvs commit: apr/locks/win32 thread_cond.c

Posted by Ryan Bloom <rb...@covalent.net>.
On Tuesday 18 September 2001 06:03 pm, Greg Stein wrote:
> On Tue, Sep 18, 2001 at 09:38:03PM -0000, rbb@apache.org wrote:
> > rbb         01/09/18 14:38:03
> >
> >   Modified:    include/arch/win32 thread_cond.h
> >                locks/win32 thread_cond.c
> >   Log:
> >   An initial thread_condition variable implementation for Windows.
> >   This is kind of ugly, but I believe it works.  It does pass all of
> >   the APR tests, and I don't see any race conditions, but other
> >   eyes are more than welcome on this code now.
> >...
> >   --- thread_cond.c	2001/09/13 01:04:23	1.1
> >   +++ thread_cond.c	2001/09/18 21:38:03	1.2
> >   @@ -60,29 +60,92 @@
> >    #include "win32/thread_cond.h"
> >    #include "apr_portable.h"
> >
> >   +static apr_status_t thread_cond_cleanup(void *data)
> >   +{
> >   +    apr_thread_cond_t *cond = data;
> >   +    if (cond->num_waiting != 0) {
> >   +        printf("somebody's waiting, but I'm closing it anyway.\n");
>
> Can't have a printf() in there. Not sure what the right answer is; maybe
> call the pool's abort function.

Actually, that shouldn't be there any more.  That was a part of my debugging.
I never saw that print out, which is why I forgot about it.

Ryan
______________________________________________________________
Ryan Bloom				rbb@apache.org
Covalent Technologies			rbb@covalent.net
--------------------------------------------------------------

Re: cvs commit: apr/locks/win32 thread_cond.c

Posted by Greg Stein <gs...@lyra.org>.
On Tue, Sep 18, 2001 at 09:38:03PM -0000, rbb@apache.org wrote:
> rbb         01/09/18 14:38:03
> 
>   Modified:    include/arch/win32 thread_cond.h
>                locks/win32 thread_cond.c
>   Log:
>   An initial thread_condition variable implementation for Windows.
>   This is kind of ugly, but I believe it works.  It does pass all of
>   the APR tests, and I don't see any race conditions, but other
>   eyes are more than welcome on this code now.
>...
>   --- thread_cond.c	2001/09/13 01:04:23	1.1
>   +++ thread_cond.c	2001/09/18 21:38:03	1.2
>   @@ -60,29 +60,92 @@
>    #include "win32/thread_cond.h"
>    #include "apr_portable.h"
>    
>   +static apr_status_t thread_cond_cleanup(void *data)
>   +{
>   +    apr_thread_cond_t *cond = data;
>   +    if (cond->num_waiting != 0) {
>   +        printf("somebody's waiting, but I'm closing it anyway.\n");

Can't have a printf() in there. Not sure what the right answer is; maybe
call the pool's abort function.

Cheers,
-g

-- 
Greg Stein, http://www.lyra.org/