SysVIPC 0.9

Sign up to get free protection for your applications and to get access to all the features.
Files changed (4) hide show
  1. data/ext/SysVIPC.c +5090 -0
  2. data/ext/extconf.rb +8 -0
  3. data/lib/SysVIPC.rb +366 -0
  4. metadata +55 -0
@@ -0,0 +1,8 @@
1
+ require 'mkmf'
2
+
3
+ if have_header('sys/types.h') and have_header('sys/ipc.h') and
4
+ have_header('sys/msg.h') and have_func('msgget') and
5
+ have_header('sys/sem.h') and have_func('semget') and
6
+ have_header('sys/shm.h') and have_func('shmget')
7
+ create_makefile('SysVIPC')
8
+ end
@@ -0,0 +1,366 @@
1
+ require 'SysVIPC.so'
2
+
3
+ # Document-class: SysVIPC
4
+ #
5
+ # = SysVIPC
6
+ #
7
+ # Ruby module for System V Inter-Process Communication:
8
+ # message queues, semaphores, and shared memory.
9
+ #
10
+ # Hosted as project sysvipc[http://rubyforge.org/projects/sysvipc/]
11
+ # on RubyForge[http://rubyforge.org/].
12
+ #
13
+ # Copyright (C) 2001, 2006, 2007 Daiki Ueno
14
+ # Copyright (C) 2006, 2007, 2009 James Steven Jenkins
15
+ #
16
+ # == Usage Synopsis
17
+ # === Common Code
18
+ #
19
+ # All programs using this module must include
20
+ #
21
+ # require 'SysVIPC'
22
+ #
23
+ # It may be convenient to add
24
+ #
25
+ # include SysVIPC
26
+ #
27
+ # All IPC objects are identified by a key. SysVIPC includes a
28
+ # convenience function for mapping file names and integer IDs into a
29
+ # key:
30
+ #
31
+ # key = ftok('/a/file/that/must/exist', 0)
32
+ #
33
+ # === Message Queues
34
+ #
35
+ # Get (create if necessary) a message queue:
36
+ #
37
+ # mq = MessageQueue.new(key, IPC_CREAT | 0600)
38
+ #
39
+ # Send a message of type 0:
40
+ #
41
+ # mq.send(0, 'message')
42
+ #
43
+ # Receive up to 100 bytes from the first message of type 0:
44
+ #
45
+ # msg = mq.receive(0, 100)
46
+ #
47
+ # === Semaphores
48
+ #
49
+ # Get (create if necessary) a set of 5 semaphores:
50
+ #
51
+ # sm = Semaphore.new(key, 5, IPC_CREAT | 0600)
52
+ #
53
+ # Initialize semaphores if newly created:
54
+ #
55
+ # sm.setall(Array.new(5, 1)) if sm.pid(0) == 0
56
+ #
57
+ # Acquire semaphore 2 (waiting if necessary):
58
+ #
59
+ # sm.op([Sembuf.new(2, -1)])
60
+ #
61
+ # Release semaphore 2:
62
+ #
63
+ # sm.op([Sembuf.new(2, 1)])
64
+ #
65
+ # === Shared Memory
66
+ #
67
+ # Get (create if necessary) an 8192-byte shared memory region:
68
+ #
69
+ # sh = SharedMemory(key, 8192, IPC_CREAT | 0660)
70
+ #
71
+ # Attach shared memory:
72
+ #
73
+ # shmaddr = sh.attach
74
+ #
75
+ # Write data:
76
+ #
77
+ # shmaddr.write('testing')
78
+ #
79
+ # Read 100 bytes of data:
80
+ #
81
+ # data = shmaddr.read(100);
82
+ #
83
+ # Detach shared memory:
84
+ #
85
+ # sh.detach(shmaddr)
86
+ #
87
+ # == Installation
88
+ #
89
+ # 1. <tt>ruby setup.rb config</tt>
90
+ # 2. <tt>ruby setup.rb setup</tt>
91
+ # 3. <tt>ruby setup.rb install</tt> (requires appropriate privilege)
92
+ #
93
+ # == Testing
94
+ #
95
+ # 1. <tt>./test_sysvipc_l</tt> (low-level interface)
96
+ # 2. <tt>./test_sysvipc_h</tt> (high-level interface)
97
+
98
+ module SysVIPC
99
+
100
+ def check_result(res) # :nodoc:
101
+ raise SystemCallError.new(SysVIPC.errno), nil, caller if res == -1
102
+ end
103
+
104
+ class MessageQueue
105
+
106
+ private
107
+
108
+ # Return a MessageQueue object encapsuating a message queue
109
+ # associated with +key+. See msgget(2).
110
+
111
+ def initialize(key, flags = 0)
112
+ @msgid = msgget(key, flags)
113
+ check_result(@msgid)
114
+ end
115
+
116
+ public
117
+
118
+ # Return the Msqid_ds object. See msgctl(2).
119
+
120
+ def ipc_stat
121
+ res, msqid_ds = msgctl(@msgid, IPC_STAT)
122
+ check_result(res)
123
+ msqid_ds
124
+ end
125
+ alias :msqid_ds :ipc_stat
126
+
127
+ # Set the Msqid_ds object. See msgctl(2).
128
+
129
+ def ipc_set(msqid_ds)
130
+ unless Msqid_ds === msqid_ds
131
+ raise ArgumentError,
132
+ "argument to ipc_set must be a Msqid_ds"
133
+ end
134
+ check_result(msgctl(@msgid, IPC_SET, msqid_ds))
135
+ end
136
+ alias :msqid_ds= :ipc_set
137
+
138
+ # Remove. See msgctl(2).
139
+
140
+ def ipc_rmid
141
+ check_result(msgctl(@msgid, IPC_RMID, nil))
142
+ end
143
+ alias :rm :ipc_rmid
144
+
145
+ # Send a message with type +type+ and text +text+. See msgsnd(2).
146
+
147
+ def snd(type, text, flags = 0)
148
+ check_result(msgsnd(@msgid, type, text, flags))
149
+ end
150
+ alias :send :snd
151
+
152
+ # Receive a message of type +type+, limited to +len+ bytes or fewer.
153
+ # See msgsnd(2).
154
+
155
+ def rcv(type, size, flags = 0)
156
+ res, mtype, mtext = msgrcv(@msgid, size, type, flags)
157
+ check_result(res)
158
+ mtext
159
+ end
160
+ alias :receive :rcv
161
+
162
+ end
163
+
164
+ class Sembuf
165
+
166
+ alias :orig_initialize :initialize
167
+
168
+ # Create a new Sembuf object for semaphore number +sem_num+,
169
+ # operation +sem_op+, and flags +sem_flg+. See semop(2).
170
+
171
+ def initialize(sem_num, sem_op, sem_flg = 0)
172
+ orig_initialize
173
+ self.sem_num = sem_num
174
+ self.sem_op = sem_op
175
+ self.sem_flg = sem_flg
176
+ end
177
+
178
+ end
179
+
180
+ class Semaphore
181
+
182
+ private
183
+
184
+ # Return a Sempahore object encapsulating a
185
+ # set of +nsems+ semaphores associated with +key+. See semget(2).
186
+
187
+ def initialize(key, nsems, flags)
188
+ @nsems = nsems
189
+ @semid = semget(key, nsems, flags)
190
+ check_result(@semid)
191
+ end
192
+
193
+ public
194
+
195
+ # Set each value in the semaphore set to the corresponding value
196
+ # in the Array +values+. See semctl(2).
197
+
198
+ def setall(values)
199
+ if values.length > @nsems
200
+ raise ArgumentError,
201
+ "too many values(#{values.length} for semaphore set (#{@nsems})"
202
+ end
203
+ check_result(semctl(@semid, 0, SETALL, values))
204
+ end
205
+
206
+ # Return an Array containing the value of each semaphore in the
207
+ # set. See semctl(2).
208
+
209
+ def getall
210
+ res, array = semctl(@semid, 0, GETALL)
211
+ check_result(res)
212
+ array
213
+ end
214
+
215
+ # Set the value of semaphore +semnum+ to +val+. See semctl(2).
216
+
217
+ def setval(semnum, val)
218
+ check_result(semctl(@semid, semnum, SETVAL, val))
219
+ end
220
+
221
+ # Get the value of semaphore +semnum+. See semctl(2).
222
+
223
+ def getval(semnum)
224
+ semctl(@semid, semnum, GETVAL)
225
+ end
226
+ alias :val :getval
227
+
228
+ # Get the process ID of the last semaphore operation. See
229
+ # semctl(2).
230
+
231
+ def getpid
232
+ semctl(@semid, 0, GETPID)
233
+ end
234
+ alias :pid :getpid
235
+
236
+ # Get the number of processes waiting for a semaphore to become
237
+ # non-zero. See semctl(2).
238
+
239
+ def getncnt
240
+ semctl(@semid, 0, GETNCNT)
241
+ end
242
+ alias :ncnt :getncnt
243
+
244
+ # Get the number of processes waiting for a semaphore to become
245
+ # zero. See semctl(2).
246
+
247
+ def getzcnt
248
+ semctl(@semid, 0, GETZCNT)
249
+ end
250
+ alias :zcnt :getzcnt
251
+
252
+ # Return the Semid_ds object. See semctl(2).
253
+
254
+ def ipc_stat
255
+ res, semid_ds = semctl(@semid, 0, IPC_STAT)
256
+ check_result(res)
257
+ semid_ds
258
+ end
259
+ alias :semid_ds :ipc_stat
260
+
261
+ # Set the Semid_ds object. See semctl(2).
262
+
263
+ def ipc_set(semid_ds)
264
+ unless Semid_ds === semid_ds
265
+ raise ArgumentError,
266
+ "argument to ipc_set must be a Semid_ds"
267
+ end
268
+ check_result(semctl(@semid, 0, IPC_SET, semid_ds))
269
+ end
270
+ alias :semid_ds= :ipc_set
271
+
272
+ # Remove. See semctl(2).
273
+
274
+ def ipc_rmid
275
+ check_result(semctl(@semid, 0, IPC_RMID))
276
+ end
277
+ alias :rm :ipc_rmid
278
+
279
+ # Perform a set of semaphore operations. The argument +array+ is
280
+ # an Array of Sembuf objects. See semop(2).
281
+
282
+ def op(array)
283
+ check_result(semop(@semid, array, array.length))
284
+ end
285
+
286
+ end
287
+
288
+ class SharedMemory
289
+
290
+ private
291
+
292
+ # Return a SharedMemory object encapsulating a
293
+ # shared memory segment of +size+ bytes associated with
294
+ # +key+. See shmget(2).
295
+
296
+ def initialize(key, size, flags = 0)
297
+ @shmid = shmget(key, size, flags)
298
+ check_result(@shmid)
299
+ end
300
+
301
+ public
302
+
303
+ # Return the Shmid_ds object. See shmctl(2).
304
+
305
+ def ipc_stat
306
+ res, shmid_ds = shmctl(@shmid, IPC_STAT)
307
+ check_result(res)
308
+ shmid_ds
309
+ end
310
+ alias :shmid_ds :ipc_stat
311
+
312
+ # Set the Shmid_ds object. See shmctl(2).
313
+
314
+ def ipc_set(shmid_ds)
315
+ unless Shmid_ds === shmid_ds
316
+ raise ArgumentError,
317
+ "argument to ipc_set must be a Shmid_ds"
318
+ end
319
+ check_result(shmctl(@shmid, IPC_SET, shmid_ds))
320
+ end
321
+ alias shmid_ds= :ipc_set
322
+
323
+ # Remove. See shmctl(2).
324
+
325
+ def ipc_rmid
326
+ check_result(shmctl(@shmid, IPC_RMID, nil))
327
+ end
328
+ alias :rm :ipc_rmid
329
+
330
+ # Attach to a shared memory address object and return it.
331
+ # See shmat(2). If +shmaddr+ is nil, the shared memory is attached
332
+ # at the first available address as selected by the system. See
333
+ # shmat(2).
334
+
335
+ def attach(shmaddr = nil, flags = 0)
336
+ shmaddr = shmat(@shmid, shmaddr, flags)
337
+ check_result(shmaddr)
338
+ shmaddr
339
+ end
340
+
341
+ # Detach the +Shmaddr+ object +shmaddr+. See shmdt(2).
342
+
343
+ def detach(shmaddr)
344
+ check_result(shmdt(shmaddr))
345
+ end
346
+
347
+ end
348
+
349
+ class Shmaddr
350
+
351
+ # Write the string +text+ to offset +offset+.
352
+
353
+ def write(text, offset = 0)
354
+ shmwrite(self, text, offset)
355
+ end
356
+ alias :<< :write
357
+
358
+ # Read +len+ bytes at offset +offset+ and return them in a String.
359
+
360
+ def read(len, offset = 0)
361
+ shmread(self, len, offset)
362
+ end
363
+
364
+ end
365
+
366
+ end
metadata ADDED
@@ -0,0 +1,55 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: SysVIPC
3
+ version: !ruby/object:Gem::Version
4
+ version: "0.9"
5
+ platform: ruby
6
+ authors:
7
+ - Steven Jenkins
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2009-07-11 00:00:00 -07:00
13
+ default_executable:
14
+ dependencies: []
15
+
16
+ description: "System V Inter-Process Communication: message queues, semaphores, and shared memory."
17
+ email: sjenkins@rubyforge.org
18
+ executables: []
19
+
20
+ extensions:
21
+ - ./ext/extconf.rb
22
+ extra_rdoc_files: []
23
+
24
+ files:
25
+ - lib/SysVIPC.rb
26
+ - ext/SysVIPC.c
27
+ has_rdoc: true
28
+ homepage: http://rubyforge.org/projects/sysvipc/
29
+ post_install_message:
30
+ rdoc_options:
31
+ - --title
32
+ - SysVIPC
33
+ require_paths:
34
+ - lib
35
+ required_ruby_version: !ruby/object:Gem::Requirement
36
+ requirements:
37
+ - - ">="
38
+ - !ruby/object:Gem::Version
39
+ version: "0"
40
+ version:
41
+ required_rubygems_version: !ruby/object:Gem::Requirement
42
+ requirements:
43
+ - - ">="
44
+ - !ruby/object:Gem::Version
45
+ version: "0"
46
+ version:
47
+ requirements: []
48
+
49
+ rubyforge_project: sysvipc
50
+ rubygems_version: 1.3.1
51
+ signing_key:
52
+ specification_version: 2
53
+ summary: Builders for MarkUp.
54
+ test_files: []
55
+