"Fossies" - the Fresh Open Source Software Archive

Member "apr-1.7.0/locks/win32/proc_mutex.c" (21 Mar 2019, 8730 Bytes) of package /linux/www/apr-1.7.0.tar.bz2:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "proc_mutex.c" see the Fossies "Dox" file reference documentation and the latest Fossies "Diffs" side-by-side code changes report: 1.6.5_vs_1.7.0.

    1 /* Licensed to the Apache Software Foundation (ASF) under one or more
    2  * contributor license agreements.  See the NOTICE file distributed with
    3  * this work for additional information regarding copyright ownership.
    4  * The ASF licenses this file to You under the Apache License, Version 2.0
    5  * (the "License"); you may not use this file except in compliance with
    6  * the License.  You may obtain a copy of the License at
    7  *
    8  *     http://www.apache.org/licenses/LICENSE-2.0
    9  *
   10  * Unless required by applicable law or agreed to in writing, software
   11  * distributed under the License is distributed on an "AS IS" BASIS,
   12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
   13  * See the License for the specific language governing permissions and
   14  * limitations under the License.
   15  */
   16 
   17 #include "apr.h"
   18 #include "apr_private.h"
   19 #include "apr_general.h"
   20 #include "apr_strings.h"
   21 #include "apr_portable.h"
   22 #include "apr_arch_file_io.h"
   23 #include "apr_arch_proc_mutex.h"
   24 #include "apr_arch_misc.h"
   25 
   26 static apr_status_t proc_mutex_cleanup(void *mutex_)
   27 {
   28     apr_proc_mutex_t *mutex = mutex_;
   29 
   30     if (mutex->handle) {
   31         if (CloseHandle(mutex->handle) == 0) {
   32             return apr_get_os_error();
   33         }
   34     }
   35     return APR_SUCCESS;
   36 }
   37 
   38 APR_DECLARE(apr_status_t) apr_proc_mutex_create(apr_proc_mutex_t **mutex,
   39                                                 const char *fname,
   40                                                 apr_lockmech_e mech,
   41                                                 apr_pool_t *pool)
   42 {
   43     HANDLE hMutex;
   44     void *mutexkey;
   45 
   46     if (mech != APR_LOCK_DEFAULT && mech != APR_LOCK_DEFAULT_TIMED) {
   47         return APR_ENOTIMPL;
   48     }
   49 
   50     /* res_name_from_filename turns fname into a pseduo-name
   51      * without slashes or backslashes, and prepends the \global
   52      * prefix on Win2K and later
   53      */
   54     if (fname) {
   55         mutexkey = res_name_from_filename(fname, 1, pool);
   56     }
   57     else {
   58         mutexkey = NULL;
   59     }
   60 
   61 #if APR_HAS_UNICODE_FS
   62     IF_WIN_OS_IS_UNICODE
   63     {
   64         hMutex = CreateMutexW(NULL, FALSE, mutexkey);
   65     }
   66 #endif
   67 #if APR_HAS_ANSI_FS
   68     ELSE_WIN_OS_IS_ANSI
   69     {
   70         hMutex = CreateMutexA(NULL, FALSE, mutexkey);
   71     }
   72 #endif
   73 
   74     if (!hMutex) {
   75         return apr_get_os_error();
   76     }
   77 
   78     *mutex = (apr_proc_mutex_t *)apr_palloc(pool, sizeof(apr_proc_mutex_t));
   79     (*mutex)->pool = pool;
   80     (*mutex)->handle = hMutex;
   81     (*mutex)->fname = fname;
   82     apr_pool_cleanup_register((*mutex)->pool, *mutex, 
   83                               proc_mutex_cleanup, apr_pool_cleanup_null);
   84     return APR_SUCCESS;
   85 }
   86 
   87 APR_DECLARE(apr_status_t) apr_proc_mutex_child_init(apr_proc_mutex_t **mutex,
   88                                                     const char *fname,
   89                                                     apr_pool_t *pool)
   90 {
   91     HANDLE hMutex;
   92     void *mutexkey;
   93 
   94     if (!fname) {
   95         /* Reinitializing unnamed mutexes is a noop in the Unix code. */
   96         return APR_SUCCESS;
   97     }
   98 
   99     /* res_name_from_filename turns file into a pseudo-name
  100      * without slashes or backslashes, and prepends the \global
  101      * prefix on Win2K and later
  102      */
  103     mutexkey = res_name_from_filename(fname, 1, pool);
  104 
  105 #if defined(_WIN32_WCE)
  106     hMutex = CreateMutex(NULL, FALSE, mutexkey);
  107     if (hMutex && ERROR_ALREADY_EXISTS != GetLastError()) {
  108         CloseHandle(hMutex);
  109         hMutex = NULL;
  110         SetLastError(ERROR_FILE_NOT_FOUND);
  111     }
  112 #else
  113 #if APR_HAS_UNICODE_FS
  114     IF_WIN_OS_IS_UNICODE
  115     {
  116         hMutex = OpenMutexW(MUTEX_ALL_ACCESS, FALSE, mutexkey);
  117     }
  118 #endif
  119 #if APR_HAS_ANSI_FS
  120     ELSE_WIN_OS_IS_ANSI
  121     {
  122         hMutex = OpenMutexA(MUTEX_ALL_ACCESS, FALSE, mutexkey);
  123     }
  124 #endif
  125 #endif
  126 
  127     if (!hMutex) {
  128         return apr_get_os_error();
  129     }
  130 
  131     *mutex = (apr_proc_mutex_t *)apr_palloc(pool, sizeof(apr_proc_mutex_t));
  132     (*mutex)->pool = pool;
  133     (*mutex)->handle = hMutex;
  134     (*mutex)->fname = fname;
  135     apr_pool_cleanup_register((*mutex)->pool, *mutex, 
  136                               proc_mutex_cleanup, apr_pool_cleanup_null);
  137     return APR_SUCCESS;
  138 }
  139     
  140 APR_DECLARE(apr_status_t) apr_proc_mutex_lock(apr_proc_mutex_t *mutex)
  141 {
  142     DWORD rv;
  143 
  144     rv = WaitForSingleObject(mutex->handle, INFINITE);
  145 
  146     if (rv == WAIT_OBJECT_0 || rv == WAIT_ABANDONED) {
  147         return APR_SUCCESS;
  148     }
  149     return apr_get_os_error();
  150 }
  151 
  152 APR_DECLARE(apr_status_t) apr_proc_mutex_trylock(apr_proc_mutex_t *mutex)
  153 {
  154     DWORD rv;
  155 
  156     rv = WaitForSingleObject(mutex->handle, 0);
  157 
  158     if (rv == WAIT_OBJECT_0 || rv == WAIT_ABANDONED) {
  159         return APR_SUCCESS;
  160     } 
  161     else if (rv == WAIT_TIMEOUT) {
  162         return APR_EBUSY;
  163     }
  164     return apr_get_os_error();
  165 }
  166 
  167 APR_DECLARE(apr_status_t) apr_proc_mutex_timedlock(apr_proc_mutex_t *mutex,
  168                                                apr_interval_time_t timeout)
  169 {
  170     DWORD rv, timeout_ms = 0;
  171     apr_interval_time_t t = timeout;
  172 
  173     do {
  174         if (t > 0) {
  175             /* Given timeout is 64bit usecs whereas Windows timeouts are
  176              * 32bit msecs and below INFINITE (2^32 - 1), so we may need
  177              * multiple timed out waits...
  178              */
  179             if (t > apr_time_from_msec(INFINITE - 1)) {
  180                 timeout_ms = INFINITE - 1;
  181                 t -= apr_time_from_msec(INFINITE - 1);
  182             }
  183             else {
  184                 timeout_ms = (DWORD)apr_time_as_msec(t);
  185                 t = 0;
  186             }
  187         }
  188         rv = WaitForSingleObject(mutex->handle, timeout_ms);
  189     } while (rv == WAIT_TIMEOUT && t > 0);
  190 
  191     if (rv == WAIT_TIMEOUT) {
  192         return APR_TIMEUP;
  193     }
  194     if (rv == WAIT_OBJECT_0 || rv == WAIT_ABANDONED) {
  195         return APR_SUCCESS;
  196     } 
  197     return apr_get_os_error();
  198 }
  199 
  200 APR_DECLARE(apr_status_t) apr_proc_mutex_unlock(apr_proc_mutex_t *mutex)
  201 {
  202     if (ReleaseMutex(mutex->handle) == 0) {
  203         return apr_get_os_error();
  204     }
  205     return APR_SUCCESS;
  206 }
  207 
  208 APR_DECLARE(apr_status_t) apr_proc_mutex_destroy(apr_proc_mutex_t *mutex)
  209 {
  210     apr_status_t stat;
  211 
  212     stat = proc_mutex_cleanup(mutex);
  213     if (stat == APR_SUCCESS) {
  214         apr_pool_cleanup_kill(mutex->pool, mutex, proc_mutex_cleanup);
  215     }
  216     return stat;
  217 }
  218 
  219 APR_DECLARE(apr_status_t) apr_proc_mutex_cleanup(void *mutex)
  220 {
  221     return apr_proc_mutex_destroy((apr_proc_mutex_t *)mutex);
  222 }
  223 
  224 APR_DECLARE(const char *) apr_proc_mutex_lockfile(apr_proc_mutex_t *mutex)
  225 {
  226     return mutex->fname;
  227 }
  228 
  229 APR_DECLARE(apr_lockmech_e) apr_proc_mutex_mech(apr_proc_mutex_t *mutex)
  230 {
  231     return APR_LOCK_DEFAULT;
  232 }
  233 
  234 APR_DECLARE(const char *) apr_proc_mutex_name(apr_proc_mutex_t *mutex)
  235 {
  236     return apr_proc_mutex_defname();
  237 }
  238 
  239 APR_DECLARE(const char *) apr_proc_mutex_defname(void)
  240 {
  241     return "win32mutex";
  242 }
  243 
  244 APR_PERMS_SET_ENOTIMPL(proc_mutex)
  245 
  246 APR_POOL_IMPLEMENT_ACCESSOR(proc_mutex)
  247 
  248 /* Implement OS-specific accessors defined in apr_portable.h */
  249 
  250 APR_DECLARE(apr_status_t) apr_os_proc_mutex_get_ex(apr_os_proc_mutex_t *ospmutex, 
  251                                                    apr_proc_mutex_t *pmutex,
  252                                                    apr_lockmech_e *mech)
  253 {
  254     *ospmutex = pmutex->handle;
  255     if (mech) {
  256         *mech = APR_LOCK_DEFAULT;
  257     }
  258     return APR_SUCCESS;
  259 }
  260 
  261 APR_DECLARE(apr_status_t) apr_os_proc_mutex_get(apr_os_proc_mutex_t *ospmutex,
  262                                                 apr_proc_mutex_t *pmutex)
  263 {
  264     return apr_os_proc_mutex_get_ex(ospmutex, pmutex, NULL);
  265 }
  266 
  267 APR_DECLARE(apr_status_t) apr_os_proc_mutex_put_ex(apr_proc_mutex_t **pmutex,
  268                                                 apr_os_proc_mutex_t *ospmutex,
  269                                                 apr_lockmech_e mech,
  270                                                 int register_cleanup,
  271                                                 apr_pool_t *pool)
  272 {
  273     if (pool == NULL) {
  274         return APR_ENOPOOL;
  275     }
  276     if (mech != APR_LOCK_DEFAULT && mech != APR_LOCK_DEFAULT_TIMED) {
  277         return APR_ENOTIMPL;
  278     }
  279 
  280     if ((*pmutex) == NULL) {
  281         (*pmutex) = (apr_proc_mutex_t *)apr_palloc(pool,
  282                                                    sizeof(apr_proc_mutex_t));
  283         (*pmutex)->pool = pool;
  284     }
  285     (*pmutex)->handle = *ospmutex;
  286 
  287     if (register_cleanup) {
  288         apr_pool_cleanup_register(pool, *pmutex, proc_mutex_cleanup,
  289                                   apr_pool_cleanup_null);
  290     }
  291     return APR_SUCCESS;
  292 }
  293 
  294 APR_DECLARE(apr_status_t) apr_os_proc_mutex_put(apr_proc_mutex_t **pmutex,
  295                                                 apr_os_proc_mutex_t *ospmutex,
  296                                                 apr_pool_t *pool)
  297 {
  298     return apr_os_proc_mutex_put_ex(pmutex, ospmutex, APR_LOCK_DEFAULT,
  299                                     0, pool);
  300 }
  301