OSDN Git Service

* Makefile.in: Add $(LIBSERVER) rule.
[pf3gnuchains/pf3gnuchains3x.git] / winsup / cygwin / cygserver_ipc.h
1 /* cygserver_ipc.h
2
3    Copyright 2002 Red Hat, Inc.
4
5    Originally written by Conrad Scott <conrad.scott@dsl.pipex.com>
6
7 This file is part of Cygwin.
8
9 This software is a copyrighted work licensed under the terms of the
10 Cygwin license.  Please consult the file "CYGWIN_LICENSE" for
11 details. */
12
13 #ifndef __CYGSERVER_IPC_H__
14 #define __CYGSERVER_IPC_H__
15
16 #include <assert.h>
17 #include <limits.h>             /* For OPEN_MAX. */
18
19 /*
20  * The sysv ipc id's (msgid, semid, shmid) are integers arranged such
21  * that they no subsystem will generate the same id as some other
22  * subsystem; nor do these ids overlap file descriptors (the other
23  * common integer ids).  Since Cygwin can allocate more than OPEN_MAX
24  * file descriptors, it can't be guaranteed not to overlap, but it
25  * should help catch some errors.
26  *
27  * msgid's: OPEN_MAX,     OPEN_MAX + 3, OPEN_MAX + 6, . . .
28  * semid's: OPEN_MAX + 1, OPEN_MAX + 4, OPEN_MAX + 7, . . .
29  * shmid's: OPEN_MAX + 2, OPEN_MAX + 5, OPEN_MAX + 8, . . .
30  *
31  * To further ensure that ids are unique, if ipc objects are created
32  * and destroyed and then re-created, they are given new ids by
33  * munging the basic id (as above) with a sequence number.
34  *
35  * Internal ipc id's, which are 0, 1, ... within each subsystem (and
36  * not munged with a sequence number), are used solely by the ipcs(8)
37  * interface.
38  */
39
40 enum ipc_subsys_t
41   {
42     IPC_MSGOP = 0,
43     IPC_SEMOP = 1,
44     IPC_SHMOP = 2,
45     IPC_SUBSYS_COUNT
46   };
47
48 /*
49  * IPCMNI - The absolute maximum number of simultaneous ipc ids for
50  * any one subsystem.
51  */
52
53 enum
54   {
55     IPCMNI = 0x10000            // Must be a power of two.
56   };
57
58 inline int
59 ipc_int2ext (const int intid, const ipc_subsys_t subsys, long & sequence)
60 {
61   assert (0 <= intid && intid < IPCMNI);
62
63   const long tmp = InterlockedIncrement (&sequence);
64
65   return (((tmp & 0x7fff) << 16)
66           | (OPEN_MAX + (intid * IPC_SUBSYS_COUNT) + subsys));
67 }
68
69 inline int
70 ipc_ext2int_subsys (const int extid)
71 {
72   return ((extid & (IPCMNI - 1)) - OPEN_MAX) % IPC_SUBSYS_COUNT;
73 }
74
75 inline int
76 ipc_ext2int (const int extid, const ipc_subsys_t subsys)
77 {
78   if (ipc_ext2int_subsys (extid) != subsys)
79     return -1;
80   else
81     return ((extid & (IPCMNI - 1)) - OPEN_MAX) / IPC_SUBSYS_COUNT;
82 }
83
84 #endif /* __CYGSERVER_IPC_H__ */