diff options
Diffstat (limited to 'winsup/cygserver/bsd_mutex.cc')
-rw-r--r-- | winsup/cygserver/bsd_mutex.cc | 267 |
1 files changed, 0 insertions, 267 deletions
diff --git a/winsup/cygserver/bsd_mutex.cc b/winsup/cygserver/bsd_mutex.cc deleted file mode 100644 index 6a9ffb2c6..000000000 --- a/winsup/cygserver/bsd_mutex.cc +++ /dev/null @@ -1,267 +0,0 @@ -/* bsd_mutex.cc - - Copyright 2003 Red Hat Inc. - -This file is part of Cygwin. - -This software is a copyrighted work licensed under the terms of the -Cygwin license. Please consult the file "CYGWIN_LICENSE" for -details. */ -#ifdef __OUTSIDE_CYGWIN__ -#include "woutsup.h" -#include "cygerrno.h" -#define _KERNEL 1 -#define __BSD_VISIBLE 1 -#include <sys/smallprint.h> - -#include "process.h" -#include "cygserver_ipc.h" - -/* A BSD kernel global mutex. */ -struct mtx Giant; - -void -mtx_init (mtx *m, const char *name, const void *, int) -{ - m->name = name; - m->owner = 0; - /* Can't use Windows Mutexes here since Windows Mutexes are only - unlockable by the lock owner. */ - m->h = CreateSemaphore (NULL, 1, 1, NULL); - if (!m->h) - panic ("couldn't allocate %s mutex, %E\n", name); -} - -void -_mtx_lock (mtx *m, DWORD winpid, const char *file, int line) -{ - _log (file, line, LOG_DEBUG, "Try locking mutex %s", m->name); - if (WaitForSingleObject (m->h, INFINITE) != WAIT_OBJECT_0) - _panic (file, line, "wait for %s in %d failed, %E", m->name, winpid); - m->owner = winpid; - _log (file, line, LOG_DEBUG, "Locked mutex %s", m->name); -} - -int -mtx_owned (mtx *m) -{ - return m->owner > 0; -} - -void -_mtx_assert(mtx *m, int what, const char *file, int line) -{ - switch (what) - { - case MA_OWNED: - if (!mtx_owned (m)) - _panic(file, line, "Mutex %s not owned", m->name); - break; - case MA_NOTOWNED: - if (mtx_owned (m)) - _panic(file, line, "Mutex %s is owned", m->name); - break; - default: - break; - } -} - -void -_mtx_unlock (mtx *m, const char *file, int line) -{ - m->owner = 0; - /* Cautiously check if mtx_destroy has been called (shutdown). - In that case, m->h is NULL. */ - if (m->h && !ReleaseSemaphore (m->h, 1, NULL)) - { - /* Check if the semaphore was already on it's max value. In this case, - ReleaseSemaphore returns FALSE with an error code which *sic* depends - on the OS. */ - if ( (!wincap.is_winnt () && GetLastError () != ERROR_INVALID_PARAMETER) - || (wincap.is_winnt () && GetLastError () != ERROR_TOO_MANY_POSTS)) - _panic (file, line, "release of mutex %s failed, %E", m->name); - } - _log (file, line, LOG_DEBUG, "Unlocked mutex %s", m->name); -} - -void -mtx_destroy (mtx *m) -{ - HANDLE tmp = m->h; - m->h = NULL; - if (tmp) - CloseHandle (tmp); -} - -/* - * Helper functions for msleep/wakeup. - */ -static char * -msleep_event_name (void *ident, char *name) -{ - if (wincap.has_terminal_services ()) - __small_sprintf (name, "Global\\cygserver.msleep.evt.%08x", ident); - else - __small_sprintf (name, "cygserver.msleep.evt.%08x", ident); - return name; -} - -static int -win_priority (int priority) -{ - int p = (int)((p) & PRIO_MASK) - PZERO; - /* Generating a valid priority value is a bit tricky. The only valid - values on 9x and NT4 are -15, -2, -1, 0, 1, 2, 15. */ - switch (p) - { - case -15: case -14: case -13: case -12: case -11: - return THREAD_PRIORITY_IDLE; - case -10: case -9: case -8: case -7: case -6: - return THREAD_PRIORITY_LOWEST; - case -5: case -4: case -3: case -2: case -1: - return THREAD_PRIORITY_BELOW_NORMAL; - case 0: - return THREAD_PRIORITY_NORMAL; - case 1: case 2: case 3: case 4: case 5: - return THREAD_PRIORITY_ABOVE_NORMAL; - case 6: case 7: case 8: case 9: case 10: - return THREAD_PRIORITY_HIGHEST; - case 11: case 12: case 13: case 14: case 15: - return THREAD_PRIORITY_TIME_CRITICAL; - } - return THREAD_PRIORITY_NORMAL; -} - -/* - * Sets the thread priority, returns the old priority. - */ -static int -set_priority (int priority) -{ - int old_prio = GetThreadPriority (GetCurrentThread ()); - if (!SetThreadPriority (GetCurrentThread (), win_priority (priority))) - log (LOG_WARNING, - "Warning: Setting thread priority to %d failed with error %lu\n", - win_priority (priority), GetLastError ()); - return old_prio; -} - -/* - * Original description from BSD code: - * - * General sleep call. Suspends the current process until a wakeup is - * performed on the specified identifier. The process will then be made - * runnable with the specified priority. Sleeps at most timo/hz seconds - * (0 means no timeout). If pri includes PCATCH flag, signals are checked - * before and after sleeping, else signals are not checked. Returns 0 if - * awakened, EWOULDBLOCK if the timeout expires. If PCATCH is set and a - * signal needs to be delivered, ERESTART is returned if the current system - * call should be restarted if possible, and EINTR is returned if the system - * call should be interrupted by the signal (return EINTR). - * - * The mutex argument is exited before the caller is suspended, and - * entered before msleep returns. If priority includes the PDROP - * flag the mutex is not entered before returning. - */ -static HANDLE msleep_glob_evt; - -void -msleep_init (void) -{ - msleep_glob_evt = CreateEvent (NULL, TRUE, FALSE, NULL); - if (!msleep_glob_evt) - panic ("CreateEvent in msleep_init failed: %E"); -} - -int -_msleep (void *ident, struct mtx *mtx, int priority, - const char *wmesg, int timo, struct thread *td) -{ - int ret = -1; - char name[64]; - msleep_event_name (ident, name); - HANDLE evt = OpenEvent (EVENT_ALL_ACCESS, FALSE, name); - if (!evt) - evt = CreateEvent (NULL, TRUE, FALSE, name); - if (!evt) - panic ("CreateEvent in msleep (%s) failed: %E", wmesg); - if (mtx) - mtx_unlock (mtx); - int old_priority = set_priority (priority); - HANDLE obj[4] = - { - evt, - msleep_glob_evt, - td->client->handle (), - td->client->signal_arrived () - }; - /* PCATCH handling. If PCATCH is given and signal_arrived is a valid - handle, then it's used in the WaitFor call and EINTR is returned. */ - int obj_cnt = 3; - if ((priority & PCATCH) - && td->client->signal_arrived () != INVALID_HANDLE_VALUE) - obj_cnt = 4; - switch (WaitForMultipleObjects (obj_cnt, obj, FALSE, timo ?: INFINITE)) - { - case WAIT_OBJECT_0: /* wakeup() has been called. */ - ret = 0; - break; - case WAIT_OBJECT_0 + 1: /* Shutdown event (triggered by wakeup_all). */ - priority |= PDROP; - /*FALLTHRU*/ - case WAIT_OBJECT_0 + 2: /* The dependent process has exited. */ - ret = EIDRM; - break; - case WAIT_OBJECT_0 + 3: /* Signal for calling process arrived. */ - ret = EINTR; - break; - case WAIT_TIMEOUT: - ret = EWOULDBLOCK; - break; - default: - panic ("wait in msleep (%s) failed, %E", wmesg); - break; - } - set_priority (old_priority); - if (!(priority & PDROP) && mtx) - mtx_lock (mtx); - CloseHandle (evt); - return ret; -} - -/* - * Make all threads sleeping on the specified identifier runnable. - */ -int -wakeup (void *ident) -{ - char name[64]; - msleep_event_name (ident, name); - HANDLE evt = OpenEvent (EVENT_MODIFY_STATE, FALSE, name); - if (!evt) - { - /* Another round of different error codes returned by 9x and NT - systems. Oh boy... */ - if ( (!wincap.is_winnt () && GetLastError () != ERROR_INVALID_NAME) - || (wincap.is_winnt () && GetLastError () != ERROR_FILE_NOT_FOUND)) - panic ("OpenEvent (%s) in wakeup failed: %E", name); - } - if (evt) - { - if (!SetEvent (evt)) - panic ("SetEvent (%s) in wakeup failed, %E", name); - CloseHandle (evt); - } - return 0; -} - -/* - * Wakeup all sleeping threads. Only called in the context of cygserver - * shutdown. - */ -void -wakeup_all (void) -{ - SetEvent (msleep_glob_evt); -} -#endif /* __OUTSIDE_CYGWIN__ */ |