Index: src/port/kill.c =================================================================== RCS file: /projects/cvsroot/pgsql/src/port/kill.c,v retrieving revision 1.6 diff -c -r1.6 kill.c *** src/port/kill.c 31 Dec 2004 22:03:53 -0000 1.6 --- src/port/kill.c 4 Jun 2005 12:16:07 -0000 *************** *** 17,61 **** #include "c.h" #ifdef WIN32 ! /* signal sending */ int pgkill(int pid, int sig) { ! char pipename[128]; ! BYTE sigData = sig; ! BYTE sigRet = 0; ! DWORD bytes; ! /* we allow signal 0 here, but it will be ignored in pg_queue_signal */ if (sig >= PG_SIGNAL_COUNT || sig < 0) ! { ! errno = EINVAL; ! return -1; ! } if (pid <= 0) ! { ! /* No support for process groups */ ! errno = EINVAL; ! return -1; ! } ! wsprintf(pipename, "\\\\.\\pipe\\pgsignal_%i", pid); ! if (!CallNamedPipe(pipename, &sigData, 1, &sigRet, 1, &bytes, 1000)) ! { ! if (GetLastError() == ERROR_FILE_NOT_FOUND) ! errno = ESRCH; ! else if (GetLastError() == ERROR_ACCESS_DENIED) ! errno = EPERM; ! else ! errno = EINVAL; ! return -1; ! } ! if (bytes != 1 || sigRet != sig) ! { ! errno = ESRCH; ! return -1; ! } ! return 0; } #endif --- 17,120 ---- #include "c.h" #ifdef WIN32 ! ! /* Convenience macro to set errno and return */ ! #define set_error_and_return(e) \ ! do{ \ ! if (shmem) UnmapViewOfFile(shmem); \ ! if (hShmem) CloseHandle(hShmem); \ ! if (hEvent) CloseHandle(hEvent); \ ! if (hMutex) CloseHandle(hMutex); \ ! \ ! errno = (e); \ ! return ((e) == 0)? 0 : -1; \ ! } while (0) ! ! /* ! * pgkill ! * kill() win32 emulation. ! * ! * pgkill() will fail if: ! * [EINVAL] The value of the sig argument is an invalid ! * or target process id <= 0. ! * [ESRCH] No process can be found corresponding to that ! * specified by pid. ! * [EPERM] Any other win32 system call fails. ! */ int pgkill(int pid, int sig) { ! char name[64]; ! HANDLE hShmem, hMutex, hEvent; ! Win32SignalShmemStruct *shmem; ! ! shmem = NULL; ! hShmem = NULL; ! hMutex = NULL; ! hEvent = NULL; ! /* we allow signal 0 here, and handle later */ if (sig >= PG_SIGNAL_COUNT || sig < 0) ! set_error_and_return(EINVAL); ! ! /* No support for process groups */ if (pid <= 0) ! set_error_and_return(EINVAL); ! ! /* ! * Attach to the signaling shared memory. If it is attachable, ! * we decide that the process is alive. ! */ ! wsprintf(name, "%s.%d", SIGNAL_SHMEM_PREFIX, pid); ! if (NULL == (hShmem = OpenFileMapping(FILE_MAP_ALL_ACCESS, ! FALSE, ! name))) ! set_error_and_return(ESRCH); ! ! if (sig == 0) ! set_error_and_return(0); ! ! if (NULL == (shmem = MapViewOfFile(hShmem, ! FILE_MAP_ALL_ACCESS, ! 0, 0, 0))) ! set_error_and_return(EPERM); ! ! /* Grab the mutex */ ! wsprintf(name, "%s.%d", SIGNAL_MUTEX_PREFIX, pid); ! if (NULL == (hMutex = OpenMutex(MUTEX_ALL_ACCESS, ! FALSE, name))) ! set_error_and_return(EPERM); ! ! if (WaitForSingleObject(hMutex, INFINITE) != WAIT_OBJECT_0) ! set_error_and_return(EPERM); ! ! /* Write down the signal number */ ! shmem->queue |= sigmask(sig); ! ! /* ! * If we can't release the mutex, we have to exit the ! * process to make mutex released by the system. If we ! * can't set the event, that's really awkward, but the ! * target process would find out the signal when next ! * set event is successfully done. ! */ ! if (!ReleaseMutex(hMutex)) ! set_error_and_return(EPERM); ! ! if (!UnmapViewOfFile(shmem)) ! set_error_and_return(EPERM); ! ! /* Set event */ ! wsprintf(name, "%s.%d", SIGNAL_EVENT_PREFIX, pid); ! if (NULL == (hEvent = OpenEvent(EVENT_ALL_ACCESS, ! FALSE, name))) ! set_error_and_return(EPERM); ! ! if (!SetEvent(hEvent)) ! set_error_and_return(EPERM); ! /* Successfully done */ ! set_error_and_return(0); } #endif