sys-proctable 0.9.3-universal-freebsd → 0.9.4-universal-freebsd

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 1c45e6ae56c6571febf5b2b7038bcc643d3cb337
4
+ data.tar.gz: f42dd07643ccc87be3ad289b8b0e9d3b2c7252cf
5
+ SHA512:
6
+ metadata.gz: 06e5a4dfbe1c74ca7fae99ceaad63adf7657fb789298fb7928f776c5684611b82927cca7b3abc4b1671771ea1383953c3f4ad91bcfb7a69cc8f2236612c6c46f
7
+ data.tar.gz: 87253dd8de985d402bc83034083c603743e4ae6ac80121a4c6b5bdfb1b58d4c0ae483071fa60205b9038887b0425ed6fe06289b2af4ce85ec49e94314f40d3cb
data/CHANGES CHANGED
@@ -1,3 +1,14 @@
1
+ == 0.9.4 - 4-Mar-2014
2
+ * Added support for AIX 5.3 or later courtesy of Rick Ohnemus.
3
+ * The Solaris version now uses FFI structs instead of a packed array.
4
+ It solved issues with 64-bit versions of Ruby and it's self-documenting.
5
+ * The FreeBSD version has been converted to use FFI. In addition, additional
6
+ struct members have been added, and members that previously returned nil
7
+ now return meaningful data.
8
+ * Support for NetBSD and OpenBSD has been temporarily dropped. Considering
9
+ that the C code did not build on those platforms anyway, I doubt most of
10
+ you will notice. Patches for those platforms are welcome, but only using FFI.
11
+
1
12
  == 0.9.3 - 17-Mar-2013
2
13
  * Fixed a bug on OSX where a long command string arg could cause
3
14
  a segfault. Thanks go to Nathaniel Bibler for the spot.
data/MANIFEST CHANGED
@@ -3,6 +3,7 @@
3
3
  * Rakefile
4
4
  * README
5
5
  * sys-proctable.gemspec
6
+ * doc/aix.txt
6
7
  * doc/bsd.txt
7
8
  * doc/hpux.txt
8
9
  * doc/linux.txt
@@ -10,20 +11,21 @@
10
11
  * doc/top.txt
11
12
  * doc/windows.txt
12
13
  * example/example_ps.rb
13
- * ext/bsd/extconf.rb
14
- * ext/bsd/sys/proctable.c
15
14
  * ext/darwin/extconf.rb
16
15
  * ext/darwin/sys/proctable.c
17
16
  * ext/hpux/extconf.rb
18
17
  * ext/hpux/sys/proctable.c
19
18
  * lib/sys/top.rb
19
+ * lib/aix/sys/proctable.rb
20
+ * lib/freebsd/sys/proctable.rb
20
21
  * lib/linux/sys/proctable.rb
21
22
  * lib/sunos/sys/proctable.rb
22
23
  * lib/windows/sys/proctable.rb
24
+ * test/test_sys_proctable_aix.rb
23
25
  * test/test_sys_proctable_all.rb
24
26
  * test/test_sys_proctable_darwin.rb
27
+ * test/test_sys_proctable_freebsd.rb
25
28
  * test/test_sys_proctable_hpux.rb
26
- * test/test_sys_proctable_bsd.rb
27
29
  * test/test_sys_proctable_linux.rb
28
30
  * test/test_sys_proctable_sunos.rb
29
31
  * test/test_sys_proctable_windows.rb
data/README CHANGED
@@ -7,7 +7,7 @@
7
7
  == Supported Platforms
8
8
  * Windows 2000 or later
9
9
  * Linux 2.6+
10
- * BSD (various flavors)
10
+ * FreeBSD
11
11
  * Solaris 8+
12
12
  * HP-UX 10+
13
13
  * OS X 10.4+
@@ -20,7 +20,7 @@
20
20
  gem install sys-proctable --platform mswin32 # Windows
21
21
  gem install sys-proctable --platform sunos # Solaris
22
22
  gem install sys-proctable --platform linux # Linux
23
- gem install sys-proctable --platform freebsd # BSD (any flavor)
23
+ gem install sys-proctable --platform freebsd # FreeBSD
24
24
 
25
25
  == Synopsis
26
26
  require 'sys/proctable'
@@ -51,7 +51,7 @@
51
51
  information from a different host. This relies on the WMI service running.
52
52
 
53
53
  == Known Issues
54
- === BSD
54
+ === FreeBSD
55
55
  A kvm interface is used. That means the owner of the process using the
56
56
  sys-proctable library needs to be a member of the kvm group (or root).
57
57
 
@@ -67,13 +67,12 @@
67
67
  Using readdir_r() still won't solve all potential thread safety issues anyway.
68
68
 
69
69
  == Future Plans
70
- Research has indicated that the kvm approach is less favored than a sysctl
71
- approach on BSD variants. I will try to add this interface in a future
72
- release.
70
+ Add support for NetBSD and OpenBSD.
71
+ Convert existing C code to FFI.
73
72
 
74
73
  == Acknowledgements
75
- This library is largely based on the Perl module Proc::ProcessTable by
76
- Dan Urist. Many ideas, as well as large chunks of code, were taken
74
+ This library was originally based on the Perl module Proc::ProcessTable
75
+ by Dan Urist. Many ideas, as well as large chunks of code, were taken
77
76
  from his work. So, a big THANK YOU goes out to Dan Urist.
78
77
 
79
78
  A big thanks also goes out to Mike Hall who was very helpful with ideas,
@@ -105,7 +104,7 @@
105
104
  Artistic 2.0
106
105
 
107
106
  == Copyright
108
- (C) 2003-2012 Daniel J. Berger
107
+ (C) 2003-2014 Daniel J. Berger
109
108
  All Rights Reserved.
110
109
 
111
110
  == Author
data/Rakefile CHANGED
@@ -8,7 +8,7 @@ CLEAN.include(
8
8
  '**/*.core', # Core dump files
9
9
  '**/*.gem', # Gem files
10
10
  '**/*.rbc', # Rubinius
11
- '.rbx', '**/*/.rbx', # Rubinius
11
+ '**/*.rbx', # Rubinius
12
12
  '**/*.o', # C object file
13
13
  '**/*.log', # Ruby extension build log
14
14
  '**/Makefile', # C Makefile
@@ -27,9 +27,6 @@ task :build => [:clean] do
27
27
  end
28
28
 
29
29
  case CONFIG['host_os']
30
- when /bsd/i
31
- dir = 'ext/bsd'
32
- ext = '.so'
33
30
  when /darwin/i
34
31
  dir = 'ext/darwin'
35
32
  ext = '.bundle'
@@ -38,7 +35,7 @@ task :build => [:clean] do
38
35
  ext = '.sl'
39
36
  end
40
37
 
41
- unless CONFIG['host_os'] =~ /win32|mswin|dos|cygwin|mingw|windows|linux|sunos|solaris/i
38
+ if CONFIG['host_os'] =~ /darwin|hpux/i
42
39
  Dir.chdir(dir) do
43
40
  ruby 'extconf.rb'
44
41
  sh 'make'
@@ -61,8 +58,10 @@ task :install => [:build] do
61
58
  file = 'lib/linux/sys/proctable.rb'
62
59
  when /sunos|solaris/i
63
60
  file = 'lib/sunos/sys/proctable.rb'
64
- when /bsd/i
65
- Dir.chdir('ext/bsd'){ sh 'make install' }
61
+ when /aix/i
62
+ file = 'lib/aix/sys/proctable.rb'
63
+ when /freebsd/i
64
+ file = 'lib/freebsd/sys/proctable.rb'
66
65
  when /darwin/i
67
66
  Dir.chdir('ext/darwin'){ sh 'make install' }
68
67
  when /hpux/i
@@ -75,12 +74,12 @@ end
75
74
  desc 'Uninstall the sys-proctable library'
76
75
  task :uninstall do
77
76
  case CONFIG['host_os']
78
- when /win32|mswin|dos|cygwin|mingw|windows|linux|sunos|solaris/i
79
- dir = File.join(CONFIG['sitelibdir'], 'sys')
80
- file = File.join(dir, 'proctable.rb')
81
- else
77
+ when /darwin|hpux/i
82
78
  dir = File.join(CONFIG['sitearchdir'], 'sys')
83
79
  file = File.join(dir, 'proctable.' + CONFIG['DLEXT'])
80
+ else
81
+ dir = File.join(CONFIG['sitelibdir'], 'sys')
82
+ file = File.join(dir, 'proctable.rb')
84
83
  end
85
84
 
86
85
  rm(file)
@@ -111,12 +110,15 @@ Rake::TestTask.new do |t|
111
110
  when /sunos|solaris/i
112
111
  t.test_files = FileList['test/test_sys_proctable_sunos.rb']
113
112
  t.libs << 'lib/sunos'
113
+ when /aix/i
114
+ t.test_files = FileList['test/test_sys_proctable_aix.rb']
115
+ t.libs << 'lib/aix'
116
+ when /freebsd/i
117
+ t.test_files = FileList['test/test_sys_proctable_freebsd.rb']
118
+ t.libs << 'lib/freebsd'
114
119
  when /darwin/i
115
120
  t.libs << 'ext/darwin'
116
121
  t.test_files = FileList['test/test_sys_proctable_darwin.rb']
117
- when /bsd/i
118
- t.libs << 'ext/bsd'
119
- t.test_files = FileList['test/test_sys_proctable_bsd.rb']
120
122
  when /hpux/i
121
123
  t.libs << 'ext/hpux'
122
124
  t.test_files = FileList['test/test_sys_proctable_hpux.rb']
@@ -133,13 +135,12 @@ namespace :gem do
133
135
  # of some bugginess in Rubygems' platform.rb.
134
136
  #
135
137
  case CONFIG['host_os']
136
- when /bsd/i
138
+ when /freebsd/i
137
139
  spec.platform = Gem::Platform.new(['universal', 'freebsd'])
138
- spec.platform.version = nil
139
- spec.files << 'ext/bsd/sys/proctable.c'
140
- spec.extra_rdoc_files << 'ext/bsd/sys/proctable.c'
141
- spec.test_files << 'test/test_sys_proctable_bsd.rb'
142
- spec.extensions = ['ext/bsd/extconf.rb']
140
+ spec.require_paths = ['lib', 'lib/freebsd']
141
+ spec.files += ['lib/freebsd/sys/proctable.rb']
142
+ spec.test_files << 'test/test_sys_proctable_freebsd.rb'
143
+ spec.add_dependency('ffi')
143
144
  when /darwin/i
144
145
  spec.platform = Gem::Platform.new(['universal', 'darwin'])
145
146
  spec.files << 'ext/darwin/sys/proctable.c'
@@ -162,6 +163,11 @@ namespace :gem do
162
163
  spec.require_paths = ['lib', 'lib/sunos']
163
164
  spec.files += ['lib/sunos/sys/proctable.rb']
164
165
  spec.test_files << 'test/test_sys_proctable_sunos.rb'
166
+ when /aix/i
167
+ spec.platform = Gem::Platform.new(['universal', 'aix5'])
168
+ spec.require_paths = ['lib', 'lib/aix']
169
+ spec.files += ['lib/aix/sys/proctable.rb']
170
+ spec.test_files << 'test/test_sys_proctable_aix.rb'
165
171
  when /mswin|win32|dos|cygwin|mingw|windows/i
166
172
  spec.platform = Gem::Platform.new(['universal', 'mingw32'])
167
173
  spec.require_paths = ['lib', 'lib/windows']
@@ -172,7 +178,12 @@ namespace :gem do
172
178
  # https://github.com/rubygems/rubygems/issues/147
173
179
  spec.original_platform = spec.platform
174
180
 
175
- Gem::Builder.new(spec).build
181
+ if Gem::VERSION < "2.0"
182
+ Gem::Builder.new(spec).build
183
+ else
184
+ require 'rubygems/package'
185
+ Gem::Package.build(spec)
186
+ end
176
187
  end
177
188
 
178
189
  desc 'Install the sys-proctable library as a gem'
@@ -0,0 +1,363 @@
1
+ require 'ffi'
2
+
3
+ module Sys
4
+ class ProcTable
5
+ extend FFI::Library
6
+
7
+ # The version of the sys-proctable library.
8
+ VERSION = '0.9.4'
9
+
10
+ # Error typically raised if the ProcTable.ps method fails.
11
+ class Error < StandardError; end
12
+
13
+ # There is no constructor
14
+ private_class_method :new
15
+
16
+ private
17
+
18
+ ffi_lib :kvm
19
+
20
+ attach_function :devname, [:dev_t, :mode_t], :string
21
+ attach_function :kvm_open, [:string, :string, :string, :int, :string], :pointer
22
+ attach_function :kvm_close, [:pointer], :int
23
+ attach_function :kvm_getprocs, [:pointer, :int, :int, :pointer], :pointer
24
+ attach_function :kvm_getargv, [:pointer, :pointer, :int], :pointer
25
+
26
+ POSIX_ARG_MAX = 4096
27
+
28
+ KERN_PROC_PID = 1
29
+ KERN_PROC_PROC = 8
30
+
31
+ S_IFCHR = 0020000
32
+
33
+ WMESGLEN = 8
34
+ LOCKNAMELEN = 8
35
+ OCOMMLEN = 16
36
+ COMMLEN = 19
37
+ KI_EMULNAMELEN = 16
38
+ KI_NGROUPS = 16
39
+ LOGNAMELEN = 17
40
+ KI_NSPARE_INT = 9
41
+ KI_NSPARE_LONG = 12
42
+ KI_NSPARE_PTR = 6
43
+
44
+ class Timeval < FFI::Struct
45
+ layout(:tv_sec, :time_t, :tv_usec, :suseconds_t)
46
+ end
47
+
48
+ class Priority < FFI::Struct
49
+ layout(
50
+ :pri_class, :uchar,
51
+ :pri_level, :uchar,
52
+ :pri_native, :uchar,
53
+ :pri_user, :uchar
54
+ )
55
+ end
56
+
57
+ class Rusage < FFI::Struct
58
+ layout(
59
+ :ru_utime, Timeval,
60
+ :ru_stime, Timeval,
61
+ :ru_maxrss, :long,
62
+ :ru_ixrss, :long,
63
+ :ru_idrss, :long,
64
+ :ru_isrss, :long,
65
+ :ru_minflt, :long,
66
+ :ru_majflt, :long,
67
+ :ru_nswap, :long,
68
+ :ru_inblock, :long,
69
+ :ru_oublock, :long,
70
+ :ru_msgsnd, :long,
71
+ :ru_msgrcv, :long,
72
+ :ru_nsignals, :long,
73
+ :ru_nvcsw, :long,
74
+ :ru_nivcsw, :long
75
+ )
76
+ end
77
+
78
+ class Pargs < FFI::Struct
79
+ layout(
80
+ :ar_ref, :uint,
81
+ :ar_length, :uint,
82
+ :ar_args, [:uchar,1]
83
+ )
84
+ end
85
+
86
+ class KInfoProc < FFI::Struct
87
+ layout(
88
+ :ki_structsize, :int,
89
+ :ki_layout, :int,
90
+ :ki_args, :pointer,
91
+ :ki_paddr, :pointer,
92
+ :ki_addr, :pointer,
93
+ :ki_tracep, :pointer,
94
+ :ki_textvp, :pointer,
95
+ :ki_fd, :pointer,
96
+ :ki_vmspace, :pointer,
97
+ :ki_wchan, :pointer,
98
+ :ki_pid, :pid_t,
99
+ :ki_ppid, :pid_t,
100
+ :ki_pgid, :pid_t,
101
+ :ki_tpgid, :pid_t,
102
+ :ki_sid, :pid_t,
103
+ :ki_tsid, :pid_t,
104
+ :ki_jobc, :short,
105
+ :ki_spare_short1, :short,
106
+ :ki_tdev, :dev_t,
107
+ :ki_siglist, [:uint32_t, 4],
108
+ :ki_sigmask, [:uint32_t, 4],
109
+ :ki_sigignore, [:uint32_t, 4],
110
+ :ki_sigcatch, [:uint32_t, 4],
111
+ :ki_uid, :uid_t,
112
+ :ki_ruid, :uid_t,
113
+ :ki_svuid, :uid_t,
114
+ :ki_rgid, :gid_t,
115
+ :ki_svgid, :gid_t,
116
+ :ki_ngroups, :short,
117
+ :ki_spare_short2, :short,
118
+ :ki_groups, [:gid_t, KI_NGROUPS],
119
+ :ki_size, :vm_size_t,
120
+ :ki_rssize, :segsz_t,
121
+ :ki_swrss, :segsz_t,
122
+ :ki_tsize, :segsz_t,
123
+ :ki_dsize, :segsz_t,
124
+ :ki_ssize, :segsz_t,
125
+ :ki_xstat, :u_short,
126
+ :ki_acflag, :u_short,
127
+ :ki_pctcpu, :fixpt_t,
128
+ :ki_estcpu, :uint,
129
+ :ki_slptime, :uint,
130
+ :ki_swtime, :uint,
131
+ :ki_swtime, :int,
132
+ :ki_runtime, :uint64_t,
133
+ :ki_start, Timeval,
134
+ :ki_childtime, Timeval,
135
+ :ki_flag, :long,
136
+ :ki_kiflag, :long,
137
+ :ki_traceflag, :int,
138
+ :ki_stat, :char,
139
+ :ki_nice, :char,
140
+ :ki_lock, :char,
141
+ :ki_rqindex, :char,
142
+ :ki_oncpu, :uchar,
143
+ :ki_lastcpu, :uchar,
144
+ :ki_ocomm, [:char, OCOMMLEN+1],
145
+ :ki_wmesg, [:char, WMESGLEN+1],
146
+ :ki_login, [:char, LOGNAMELEN+1],
147
+ :ki_lockname, [:char, LOCKNAMELEN+1],
148
+ :ki_comm, [:char, COMMLEN+1],
149
+ :ki_emul, [:char, KI_EMULNAMELEN+1],
150
+ :ki_sparestrings, [:char, 68],
151
+ :ki_spareints, [:int, KI_NSPARE_INT],
152
+ :ki_cr_flags, :uint,
153
+ :ki_jid, :int,
154
+ :ki_numthreads, :int,
155
+ :ki_tid, :lwpid_t,
156
+ :ki_pri, Priority,
157
+ :ki_rusage, Rusage,
158
+ :ki_rusage_ch, Rusage,
159
+ :ki_pcb, :pointer,
160
+ :ki_kstack, :pointer,
161
+ :ki_udata, :pointer,
162
+ :ki_tdaddr, :pointer,
163
+ :ki_spareptrs, [:pointer, KI_NSPARE_PTR],
164
+ :ki_sparelongs, [:long, KI_NSPARE_LONG],
165
+ :ki_sflags, :long,
166
+ :ki_tdflags, :long
167
+ )
168
+ end
169
+
170
+ @fields = %w[
171
+ pid ppid pgid tpgid sid tsid jobc uid ruid rgid
172
+ ngroups groups size rssize swrss tsize dsize ssize
173
+ xstat acflag pctcpu estcpu slptime swtime runtime start
174
+ flag state nice lock rqindex oncpu lastcpu wmesg login
175
+ lockname comm ttynum ttydev jid priority usrpri cmdline
176
+ utime stime maxrss ixrss idrss isrss minflt majflt nswap
177
+ inblock oublock msgsnd msgrcv nsignals nvcsw nivcsw
178
+ ]
179
+
180
+ ProcTableStruct = Struct.new('ProcTableStruct', *@fields)
181
+
182
+ public
183
+
184
+ # In block form, yields a ProcTableStruct for each process entry that you
185
+ # have rights to. This method returns an array of ProcTableStruct's in
186
+ # non-block form.
187
+ #
188
+ # If a +pid+ is provided, then only a single ProcTableStruct is yielded or
189
+ # returned, or nil if no process information is found for that +pid+.
190
+ #
191
+ # Example:
192
+ #
193
+ # # Iterate over all processes
194
+ # ProcTable.ps do |proc_info|
195
+ # p proc_info
196
+ # end
197
+ #
198
+ # # Print process table information for only pid 1001
199
+ # p ProcTable.ps(1001)
200
+ #
201
+ def self.ps(pid = nil)
202
+ begin
203
+ kd = kvm_open(nil, nil, nil, 0, nil)
204
+
205
+ if kd.null?
206
+ raise SystemCallError.new('kvm_open', FFI.errno)
207
+ end
208
+
209
+ ptr = FFI::MemoryPointer.new(:int) # count
210
+
211
+ if pid
212
+ procs = kvm_getprocs(kd, KERN_PROC_PID, pid, ptr)
213
+ else
214
+ procs = kvm_getprocs(kd, KERN_PROC_PROC, 0, ptr)
215
+ end
216
+
217
+ if procs.null?
218
+ if pid && FFI.errno == Errno::ESRCH::Errno
219
+ return nil
220
+ else
221
+ raise SystemCallError.new('kvm_getprocs', FFI.errno)
222
+ end
223
+ end
224
+
225
+ count = ptr.read_int
226
+ array = []
227
+
228
+ 0.upto(count-1){ |i|
229
+ cmd = nil
230
+ kinfo = KInfoProc.new(procs[i * KInfoProc.size])
231
+
232
+ args = kvm_getargv(kd, kinfo, 0)
233
+
234
+ unless args.null?
235
+ cmd = []
236
+
237
+ until ((ptr = args.read_pointer).null?)
238
+ cmd << ptr.read_string
239
+ args += FFI::Type::POINTER.size
240
+ end
241
+
242
+ cmd = cmd.join(' ')
243
+ end
244
+
245
+ struct = ProcTableStruct.new(
246
+ kinfo[:ki_pid],
247
+ kinfo[:ki_ppid],
248
+ kinfo[:ki_pgid],
249
+ kinfo[:ki_tpgid],
250
+ kinfo[:ki_sid],
251
+ kinfo[:ki_tsid],
252
+ kinfo[:ki_jobc],
253
+ kinfo[:ki_uid],
254
+ kinfo[:ki_ruid],
255
+ kinfo[:ki_rgid],
256
+ kinfo[:ki_ngroups],
257
+ kinfo[:ki_groups].to_a[0...kinfo[:ki_ngroups]],
258
+ kinfo[:ki_size],
259
+ kinfo[:ki_rssize],
260
+ kinfo[:ki_swrss],
261
+ kinfo[:ki_tsize],
262
+ kinfo[:ki_dsize],
263
+ kinfo[:ki_ssize],
264
+ kinfo[:ki_xstat],
265
+ kinfo[:ki_acflag],
266
+ kinfo[:ki_pctcpu].to_f,
267
+ kinfo[:ki_estcpu],
268
+ kinfo[:ki_slptime],
269
+ kinfo[:ki_swtime],
270
+ kinfo[:ki_runtime],
271
+ Time.at(kinfo[:ki_start][:tv_sec]),
272
+ kinfo[:ki_flag],
273
+ get_state(kinfo[:ki_stat]),
274
+ kinfo[:ki_nice],
275
+ kinfo[:ki_lock],
276
+ kinfo[:ki_rqindex],
277
+ kinfo[:ki_oncpu],
278
+ kinfo[:ki_lastcpu],
279
+ kinfo[:ki_wmesg].to_s,
280
+ kinfo[:ki_login].to_s,
281
+ kinfo[:ki_lockname].to_s,
282
+ kinfo[:ki_comm].to_s,
283
+ kinfo[:ki_tdev],
284
+ devname(kinfo[:ki_tdev], S_IFCHR),
285
+ kinfo[:ki_jid],
286
+ kinfo[:ki_pri][:pri_level],
287
+ kinfo[:ki_pri][:pri_user],
288
+ cmd,
289
+ kinfo[:ki_rusage][:ru_utime][:tv_sec],
290
+ kinfo[:ki_rusage][:ru_stime][:tv_sec],
291
+ kinfo[:ki_rusage][:ru_maxrss],
292
+ kinfo[:ki_rusage][:ru_ixrss],
293
+ kinfo[:ki_rusage][:ru_idrss],
294
+ kinfo[:ki_rusage][:ru_isrss],
295
+ kinfo[:ki_rusage][:ru_minflt],
296
+ kinfo[:ki_rusage][:ru_majflt],
297
+ kinfo[:ki_rusage][:ru_nswap],
298
+ kinfo[:ki_rusage][:ru_inblock],
299
+ kinfo[:ki_rusage][:ru_oublock],
300
+ kinfo[:ki_rusage][:ru_msgsnd],
301
+ kinfo[:ki_rusage][:ru_msgrcv],
302
+ kinfo[:ki_rusage][:ru_nsignals],
303
+ kinfo[:ki_rusage][:ru_nvcsw],
304
+ kinfo[:ki_rusage][:ru_nivcsw]
305
+ )
306
+
307
+ struct.freeze # This is readonly data
308
+
309
+ if block_given?
310
+ yield struct
311
+ else
312
+ array << struct
313
+ end
314
+ }
315
+ ensure
316
+ kvm_close(kd) unless kd.null?
317
+ end
318
+
319
+ if block_given?
320
+ nil
321
+ else
322
+ pid ? array.first : array
323
+ end
324
+ end
325
+
326
+ # Returns an array of fields that each ProcTableStruct will contain. This
327
+ # may be useful if you want to know in advance what fields are available
328
+ # without having to perform at least one read of the /proc table.
329
+ #
330
+ # Example:
331
+ #
332
+ # Sys::ProcTable.fields.each{ |field|
333
+ # puts "Field: #{field}"
334
+ # }
335
+ #
336
+ def self.fields
337
+ @fields
338
+ end
339
+
340
+ private
341
+
342
+ SIDL = 1
343
+ SRUN = 2
344
+ SSLEEP = 3
345
+ SSTOP = 4
346
+ SZOMB = 5
347
+ SWAIT = 6
348
+ SLOCK = 7
349
+
350
+ def self.get_state(int)
351
+ case int
352
+ when SIDL; "idle"
353
+ when SRUN; "run"
354
+ when SSLEEP; "sleep"
355
+ when SSTOP; "stop"
356
+ when SZOMB; "zombie"
357
+ when SWAIT; "waiting"
358
+ when SLOCK; "locked"
359
+ else; "unknown"
360
+ end
361
+ end
362
+ end
363
+ end
@@ -7,19 +7,21 @@ module Sys
7
7
  class Top
8
8
 
9
9
  # The version of the sys-top library
10
- VERSION = '1.0.3'
10
+ VERSION = '1.0.4'
11
11
 
12
12
  # Returns an array of Struct::ProcTableStruct elements containing up
13
13
  # to +num+ elements, sorted by +field+. The default number of elements
14
14
  # is 10, while the default field is 'pctcpu'.
15
15
  #
16
- # Exception: the default sort field is 'pid' on Linux and Windows.
16
+ # Exception: the default sort field is 'pid' on AIX and Windows.
17
17
  #
18
18
  def self.top(num=10, field='pctcpu')
19
19
  field = field.to_s if field.is_a?(Symbol)
20
20
 
21
- # Sort by pid on Windows by default
22
- if File::ALT_SEPARATOR && field == 'pctcpu'
21
+ aix = RbConfig::CONFIG['host_os'] =~ /aix/i
22
+
23
+ # Sort by pid on Windows and AIX by default
24
+ if (File::ALT_SEPARATOR || aix) && field == 'pctcpu'
23
25
  field = 'pid'
24
26
  end
25
27
 
@@ -2,7 +2,7 @@ require 'rubygems'
2
2
 
3
3
  Gem::Specification.new do |spec|
4
4
  spec.name = 'sys-proctable'
5
- spec.version = '0.9.3'
5
+ spec.version = '0.9.4'
6
6
  spec.author = 'Daniel J. Berger'
7
7
  spec.license = 'Artistic 2.0'
8
8
  spec.email = 'djberg96@gmail.com'
@@ -26,7 +26,8 @@ Gem::Specification.new do |spec|
26
26
  spec.rubyforge_project = 'sysutils'
27
27
  spec.extra_rdoc_files = ['CHANGES', 'README', 'MANIFEST', 'doc/top.txt']
28
28
 
29
- spec.add_development_dependency('test-unit', '>= 2.4.0')
29
+ spec.add_development_dependency('test-unit')
30
+ spec.add_development_dependency('rake')
30
31
 
31
32
  spec.description = <<-EOF
32
33
  The sys-proctable library provides an interface for gathering information
@@ -4,10 +4,7 @@
4
4
  # Test suite for methods common to all platforms. Generally speaking
5
5
  # you should run this test case using the 'rake test' task.
6
6
  #######################################################################
7
- require 'rubygems'
8
- gem 'test-unit'
9
-
10
- require 'test/unit'
7
+ require 'test-unit'
11
8
  require 'sys/proctable'
12
9
  require 'test/test_sys_top'
13
10
  include Sys
@@ -22,7 +19,7 @@ class TC_ProcTable_All < Test::Unit::TestCase
22
19
  end
23
20
 
24
21
  def test_version
25
- assert_equal('0.9.3', ProcTable::VERSION)
22
+ assert_equal('0.9.4', ProcTable::VERSION)
26
23
  end
27
24
 
28
25
  def test_fields
@@ -1,29 +1,29 @@
1
1
  ################################################################
2
- # test_sys_proctable_bsd.rb
2
+ # test_sys_proctable_freebsd.rb
3
3
  #
4
- # Test suite for various BSD flavors for the sys-proctable
5
- # library. You should run these tests via 'rake test'.
4
+ # Test suite for FreeBSD for the sys-proctable library.
5
+ # You should run these tests via 'rake test'.
6
6
  ################################################################
7
- require 'rubygems'
8
- gem 'test-unit'
9
-
10
- require 'test/unit'
7
+ require 'test-unit'
11
8
  require 'sys/proctable'
12
9
  require 'test/test_sys_proctable_all'
13
10
  include Sys
14
11
 
15
- class TC_Sys_ProcTable_BSD < Test::Unit::TestCase
12
+ class TC_Sys_ProcTable_FreeBSD < Test::Unit::TestCase
16
13
  def self.startup
17
- @@fields = %w/
18
- pid ppid pgid ruid rgid comm state pctcpu oncpu ttynum ttydev
19
- wmesg time priority usrpri nice cmdline start
20
- maxrss ixrss idrss isrss minflt majflt nswap inblock oublock
21
- msgsnd msgrcv nsignals nvcsw nivcsw utime stime
22
- /
14
+ @@fields = %w[
15
+ pid ppid pgid tpgid sid tsid jobc uid ruid rgid
16
+ ngroups groups size rssize swrss tsize dsize ssize
17
+ xstat acflag pctcpu estcpu slptime swtime runtime start
18
+ flag state nice lock rqindex oncpu lastcpu wmesg login
19
+ lockname comm ttynum ttydev jid priority usrpri cmdline
20
+ utime stime maxrss ixrss idrss isrss minflt majflt nswap
21
+ inblock oublock msgsnd msgrcv nsignals nvcsw nivcsw
22
+ ]
23
23
  end
24
24
 
25
25
  def setup
26
- @ptable = ProcTable.ps.last
26
+ @ptable = ProcTable.ps(Process.pid)
27
27
  end
28
28
 
29
29
  def test_fields
@@ -92,9 +92,9 @@ class TC_Sys_ProcTable_BSD < Test::Unit::TestCase
92
92
  assert_kind_of(String, @ptable.wmesg)
93
93
  end
94
94
 
95
- def test_time
96
- assert_respond_to(@ptable, :time)
97
- assert_kind_of(Fixnum, @ptable.time)
95
+ def test_runtime
96
+ assert_respond_to(@ptable, :runtime)
97
+ assert_kind_of(Fixnum, @ptable.runtime)
98
98
  end
99
99
 
100
100
  def test_priority
@@ -124,82 +124,82 @@ class TC_Sys_ProcTable_BSD < Test::Unit::TestCase
124
124
 
125
125
  def test_maxrss
126
126
  assert_respond_to(@ptable, :maxrss)
127
- assert_true(@ptable.maxrss.kind_of?(Fixnum) || @ptable.maxrss.nil?)
127
+ assert_kind_of(Fixnum, @ptable.maxrss)
128
128
  end
129
129
 
130
130
  def test_ixrss
131
131
  assert_respond_to(@ptable, :ixrss)
132
- assert_true(@ptable.ixrss.kind_of?(Fixnum) || @ptable.ixrss.nil?)
132
+ assert_kind_of(Fixnum, @ptable.ixrss)
133
133
  end
134
134
 
135
135
  def test_idrss
136
136
  assert_respond_to(@ptable, :idrss)
137
- assert_true(@ptable.idrss.kind_of?(Fixnum) || @ptable.idrss.nil?)
137
+ assert_kind_of(Fixnum, @ptable.idrss)
138
138
  end
139
139
 
140
140
  def test_isrss
141
141
  assert_respond_to(@ptable, :isrss)
142
- assert_true(@ptable.isrss.kind_of?(Fixnum) || @ptable.isrss.nil?)
142
+ assert_kind_of(Fixnum, @ptable.isrss)
143
143
  end
144
144
 
145
145
  def test_minflt
146
146
  assert_respond_to(@ptable, :minflt)
147
- assert_true(@ptable.minflt.kind_of?(Fixnum) || @ptable.minflt.nil?)
147
+ assert_kind_of(Fixnum, @ptable.minflt)
148
148
  end
149
149
 
150
150
  def test_majflt
151
151
  assert_respond_to(@ptable, :majflt)
152
- assert_true(@ptable.majflt.kind_of?(Fixnum) || @ptable.majflt.nil?)
152
+ assert_kind_of(Fixnum, @ptable.majflt)
153
153
  end
154
154
 
155
155
  def test_nswap
156
156
  assert_respond_to(@ptable, :nswap)
157
- assert_true(@ptable.nswap.kind_of?(Fixnum) || @ptable.nswap.nil?)
157
+ assert_kind_of(Fixnum, @ptable.nswap)
158
158
  end
159
159
 
160
160
  def test_inblock
161
161
  assert_respond_to(@ptable, :inblock)
162
- assert_true(@ptable.inblock.kind_of?(Fixnum) || @ptable.inblock.nil?)
162
+ assert_kind_of(Fixnum, @ptable.inblock)
163
163
  end
164
164
 
165
165
  def test_oublock
166
166
  assert_respond_to(@ptable, :oublock)
167
- assert_true(@ptable.oublock.kind_of?(Fixnum) || @ptable.oublock.nil?)
167
+ assert_kind_of(Fixnum, @ptable.oublock)
168
168
  end
169
169
 
170
170
  def test_msgsnd
171
171
  assert_respond_to(@ptable, :msgsnd)
172
- assert_true(@ptable.msgsnd.kind_of?(Fixnum) || @ptable.msgsnd.nil?)
172
+ assert_kind_of(Fixnum, @ptable.msgsnd)
173
173
  end
174
174
 
175
175
  def test_msgrcv
176
176
  assert_respond_to(@ptable, :msgrcv)
177
- assert_true(@ptable.msgrcv.kind_of?(Fixnum) || @ptable.msgrcv.nil?)
177
+ assert_kind_of(Fixnum, @ptable.msgrcv)
178
178
  end
179
179
 
180
180
  def test_nsignals
181
181
  assert_respond_to(@ptable, :nsignals)
182
- assert_true(@ptable.nsignals.kind_of?(Fixnum) || @ptable.nsignals.nil?)
182
+ assert_kind_of(Fixnum, @ptable.nsignals)
183
183
  end
184
184
 
185
185
  def test_nvcsw
186
186
  assert_respond_to(@ptable, :nvcsw)
187
- assert_true(@ptable.nvcsw.kind_of?(Fixnum) || @ptable.nvcsw.nil?)
187
+ assert_kind_of(Fixnum, @ptable.nvcsw)
188
188
  end
189
189
 
190
190
  def test_nivcsw
191
191
  assert_respond_to(@ptable, :nivcsw)
192
- assert_true(@ptable.nivcsw.kind_of?(Fixnum) || @ptable.nivcsw.nil?)
192
+ assert_kind_of(Fixnum, @ptable.nivcsw)
193
193
  end
194
194
 
195
195
  def test_utime
196
196
  assert_respond_to(@ptable, :utime)
197
- assert_true(@ptable.utime.kind_of?(Fixnum) || @ptable.utime.nil?)
197
+ assert_kind_of(Fixnum, @ptable.utime)
198
198
  end
199
199
 
200
200
  def test_stime
201
201
  assert_respond_to(@ptable, :stime)
202
- assert_true(@ptable.stime.kind_of?(Fixnum) || @ptable.stime.nil?)
202
+ assert_kind_of(Fixnum, @ptable.stime)
203
203
  end
204
204
 
205
205
  def teardown
metadata CHANGED
@@ -1,97 +1,109 @@
1
- --- !ruby/object:Gem::Specification
1
+ --- !ruby/object:Gem::Specification
2
2
  name: sys-proctable
3
- version: !ruby/object:Gem::Version
4
- hash: 61
5
- prerelease:
6
- segments:
7
- - 0
8
- - 9
9
- - 3
10
- version: 0.9.3
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.9.4
11
5
  platform: universal-freebsd
12
- authors:
6
+ authors:
13
7
  - Daniel J. Berger
14
8
  autorequire:
15
9
  bindir: bin
16
10
  cert_chain: []
17
-
18
- date: 2012-12-08 00:00:00 Z
19
- dependencies:
20
- - !ruby/object:Gem::Dependency
11
+ date: 2014-03-04 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
21
14
  name: test-unit
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :development
22
21
  prerelease: false
23
- requirement: &id001 !ruby/object:Gem::Requirement
24
- none: false
25
- requirements:
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: rake
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
26
31
  - - ">="
27
- - !ruby/object:Gem::Version
28
- hash: 31
29
- segments:
30
- - 2
31
- - 4
32
- - 0
33
- version: 2.4.0
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
34
  type: :development
35
- version_requirements: *id001
36
- description: " The sys-proctable library provides an interface for gathering information\n about processes on your system, i.e. the process table. Most major\n platforms are supported and, while different platforms may return\n different information, the external interface is identical across\n platforms.\n"
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: ffi
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: '0'
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
55
+ description: |2
56
+ The sys-proctable library provides an interface for gathering information
57
+ about processes on your system, i.e. the process table. Most major
58
+ platforms are supported and, while different platforms may return
59
+ different information, the external interface is identical across
60
+ platforms.
37
61
  email: djberg96@gmail.com
38
62
  executables: []
39
-
40
- extensions:
41
- - ext/bsd/extconf.rb
42
- extra_rdoc_files:
63
+ extensions: []
64
+ extra_rdoc_files:
43
65
  - CHANGES
44
66
  - README
45
67
  - MANIFEST
46
68
  - doc/top.txt
47
- - ext/bsd/sys/proctable.c
48
- files:
49
- - benchmarks/bench_ps.rb
50
- - examples/example_ps.rb
51
- - lib/sys/top.rb
69
+ files:
52
70
  - CHANGES
53
71
  - MANIFEST
54
- - Rakefile
55
72
  - README
73
+ - Rakefile
74
+ - benchmarks/bench_ps.rb
75
+ - doc/top.txt
76
+ - examples/example_ps.rb
77
+ - lib/freebsd/sys/proctable.rb
78
+ - lib/sys/top.rb
56
79
  - sys-proctable.gemspec
57
80
  - test/test_sys_proctable_all.rb
58
- - doc/top.txt
59
- - ext/bsd/sys/proctable.c
60
- - test/test_sys_proctable_bsd.rb
61
- - ext/bsd/extconf.rb
81
+ - test/test_sys_proctable_freebsd.rb
62
82
  homepage: http://www.rubyforge.org/projects/sysutils
63
- licenses:
83
+ licenses:
64
84
  - Artistic 2.0
85
+ metadata: {}
65
86
  post_install_message:
66
87
  rdoc_options: []
67
-
68
- require_paths:
88
+ require_paths:
69
89
  - lib
70
- required_ruby_version: !ruby/object:Gem::Requirement
71
- none: false
72
- requirements:
90
+ - lib/freebsd
91
+ required_ruby_version: !ruby/object:Gem::Requirement
92
+ requirements:
73
93
  - - ">="
74
- - !ruby/object:Gem::Version
75
- hash: 3
76
- segments:
77
- - 0
78
- version: "0"
79
- required_rubygems_version: !ruby/object:Gem::Requirement
80
- none: false
81
- requirements:
94
+ - !ruby/object:Gem::Version
95
+ version: '0'
96
+ required_rubygems_version: !ruby/object:Gem::Requirement
97
+ requirements:
82
98
  - - ">="
83
- - !ruby/object:Gem::Version
84
- hash: 3
85
- segments:
86
- - 0
87
- version: "0"
99
+ - !ruby/object:Gem::Version
100
+ version: '0'
88
101
  requirements: []
89
-
90
102
  rubyforge_project: sysutils
91
- rubygems_version: 1.8.10
103
+ rubygems_version: 2.2.2
92
104
  signing_key:
93
- specification_version: 3
105
+ specification_version: 4
94
106
  summary: An interface for providing process table information
95
- test_files:
107
+ test_files:
96
108
  - test/test_sys_proctable_all.rb
97
- - test/test_sys_proctable_bsd.rb
109
+ - test/test_sys_proctable_freebsd.rb
@@ -1,14 +0,0 @@
1
- require 'mkmf'
2
-
3
- have_type('rb_pid_t', 'ruby.h')
4
-
5
- have_library('kvm')
6
- have_func('kvm_openfiles')
7
- have_struct_member('struct kinfo_proc', 'kp_proc', 'sys/user.h')
8
- have_struct_member('struct kinfo_proc', 'kp_eproc', 'sys/user.h')
9
- have_struct_member('struct kinfo_proc', 'u_kproc', 'sys/user.h')
10
- have_struct_member('struct eproc', 'e_stats', 'sys/sysctl.h')
11
- have_struct_member('struct eproc', 'p_oncpu', 'sys/sysctl.h')
12
- have_struct_member('struct eproc', 'p_runtime', 'sys/sysctl.h')
13
-
14
- create_makefile('sys/proctable', 'sys')
@@ -1,301 +0,0 @@
1
- /**********************************************************************
2
- * proctable.c
3
- *
4
- * This is a generic kvm interface used by the various BSD flavors
5
- * for the sys-proctable library.
6
- **********************************************************************/
7
- #include "ruby.h"
8
- #include <kvm.h>
9
- #include <sys/param.h>
10
- #include <sys/stat.h>
11
- #include <sys/sysctl.h>
12
- #include <sys/types.h>
13
- #include <sys/user.h>
14
-
15
- #define SYS_PROCTABLE_VERSION "0.9.3"
16
-
17
- VALUE cProcTableError, sProcStruct;
18
-
19
- const char* fields[] = {
20
- "pid", "ppid", "pgid", "ruid",
21
- "rgid", "comm", "state", "pctcpu", "oncpu", "ttynum", "ttydev", "wmesg",
22
- "time", "priority", "usrpri", "nice", "cmdline", "start",
23
- "maxrss", "ixrss", "idrss", "isrss", "minflt", "majflt", "nswap",
24
- "inblock", "oublock", "msgsnd", "msgrcv", "nsignals", "nvcsw", "nivcsw",
25
- "utime", "stime"
26
- };
27
-
28
- /*
29
- * call-seq:
30
- * ProcTable.ps(pid=nil)
31
- * ProcTable.ps(pid=nil){ |ps| ... }
32
- *
33
- * In block form, yields a ProcTableStruct for each process entry that you
34
- * have rights to. This method returns an array of ProcTableStruct's in
35
- * non-block form.
36
- *
37
- * If a +pid+ is provided, then only a single ProcTableStruct is yielded or
38
- * returned, or nil if no process information is found for that +pid+.
39
- */
40
- static VALUE pt_ps(int argc, VALUE* argv, VALUE klass){
41
- kvm_t *kd;
42
- char errbuf[_POSIX2_LINE_MAX];
43
- char cmdline[_POSIX_ARG_MAX+1];
44
- char state[8];
45
- char** args = malloc(sizeof(char*));
46
- struct kinfo_proc* procs;
47
- int count; // Holds total number of processes
48
- int i = 0;
49
- VALUE v_pid, v_tty_num, v_tty_dev, v_start_time;
50
- VALUE v_pstruct = Qnil;
51
- VALUE v_array = Qnil;
52
-
53
- rb_scan_args(argc, argv, "01", &v_pid);
54
-
55
- if(!NIL_P(v_pid))
56
- Check_Type(v_pid, T_FIXNUM);
57
-
58
- if(!rb_block_given_p())
59
- v_array = rb_ary_new();
60
-
61
- // Open the kvm interface, get a descriptor
62
- if((kd = kvm_open(NULL, NULL, NULL, 0, "kvm_open")) == NULL)
63
- rb_raise(cProcTableError, "kvm_open failed: %s", strerror(errno));
64
-
65
- // Get the list of processes
66
- if((procs = kvm_getprocs(kd, KERN_PROC_ALL, 0, &count)) == NULL) {
67
- strcpy(errbuf, kvm_geterr(kd));
68
- kvm_close(kd);
69
- rb_raise(cProcTableError, errbuf);
70
- }
71
-
72
- for(i=0; i<count; i++){
73
- // Reset some variables
74
- v_tty_num = Qnil;
75
- v_tty_dev = Qnil;
76
- v_start_time = Qnil;
77
-
78
- // If a PID is provided, skip unless the PID matches
79
- if(!NIL_P(v_pid)){
80
- #ifdef HAVE_ST_KP_PROC
81
- if(procs[i].kp_proc.p_pid != NUM2INT(v_pid))
82
- continue;
83
- #else
84
- if(procs[i].ki_pid != NUM2INT(v_pid))
85
- continue;
86
- #endif
87
- }
88
-
89
- // Get the command line arguments for the process
90
- cmdline[0] = '\0';
91
- args = kvm_getargv(kd, (const struct kinfo_proc *)&procs[i], 0);
92
-
93
- if(args){
94
- int j = 0;
95
- while (args[j] && strlen(cmdline) <= _POSIX_ARG_MAX) {
96
- strcat(cmdline, args[j]);
97
- strcat(cmdline, " ");
98
- j++;
99
- }
100
- }
101
-
102
- // Get the start time of the process
103
- v_start_time = rb_time_new(
104
- #ifdef HAVE_ST_E_STATS
105
- procs[i].kp_eproc.e_stats.p_start.tv_sec,
106
- procs[i].kp_eproc.e_stats.p_start.tv_usec
107
- #else
108
- 0,0
109
- #endif
110
- );
111
-
112
- // Get the state of the process
113
- #ifdef HAVE_ST_KP_PROC
114
- switch(procs[i].kp_proc.p_stat)
115
- #else
116
- switch(procs[i].ki_stat)
117
- #endif
118
- {
119
- case SIDL:
120
- strcpy(state, "idle");
121
- break;
122
- case SRUN:
123
- strcpy(state, "run");
124
- break;
125
- case SSLEEP:
126
- strcpy(state, "sleep");
127
- break;
128
- case SSTOP:
129
- strcpy(state, "stop");
130
- break;
131
- case SZOMB:
132
- strcpy(state, "zombie");
133
- break;
134
- default:
135
- strcpy(state, "unknown");
136
- break;
137
- }
138
-
139
- // Get ttynum and ttydev. If ttynum is -1, there is no tty
140
- #ifdef HAVE_ST_KP_EPROC
141
- v_tty_num = INT2FIX(procs[i].kp_eproc.e_tdev),
142
- v_tty_dev = rb_str_new2(devname(procs[i].kp_eproc.e_tdev, S_IFCHR));
143
- #elif HAVE_ST_U_KPROC
144
- v_tty_num = INT2FIX(procs[i].u_kproc.ki_tdev),
145
- v_tty_dev = rb_str_new2(devname(procs[i].u_kproc.ki_tdev, S_IFCHR));
146
- #else
147
- v_tty_num = INT2FIX(procs[i].ki_tdev),
148
- v_tty_dev = rb_str_new2(devname(procs[i].ki_tdev, S_IFCHR));
149
- #endif
150
-
151
- #ifdef HAVE_ST_KP_PROC
152
- v_pstruct = rb_struct_new(
153
- sProcStruct,
154
- INT2FIX(procs[i].kp_proc.p_pid),
155
- INT2FIX(procs[i].kp_eproc.e_ppid),
156
- INT2FIX(procs[i].kp_eproc.e_pgid),
157
- INT2FIX(procs[i].kp_eproc.e_pcred.p_ruid),
158
- INT2FIX(procs[i].kp_eproc.e_pcred.p_rgid),
159
- rb_str_new2(procs[i].kp_proc.p_comm),
160
- rb_str_new2(state),
161
- rb_float_new(procs[i].kp_proc.p_pctcpu),
162
- #ifdef HAVE_ST_P_ONCPU
163
- INT2FIX(procs[i].kp_proc.p_oncpu),
164
- #else
165
- Qnil,
166
- #endif
167
- v_tty_num,
168
- v_tty_dev,
169
- rb_str_new2(procs[i].kp_eproc.e_wmesg),
170
- #ifdef HAVE_ST_P_RUNTIME
171
- INT2FIX(procs[i].kp_proc.p_runtime/1000000),
172
- #else
173
- Qnil,
174
- #endif
175
- INT2FIX(procs[i].kp_proc.p_priority),
176
- INT2FIX(procs[i].kp_proc.p_usrpri),
177
- INT2FIX(procs[i].kp_proc.p_nice),
178
- rb_str_new2(cmdline),
179
- v_start_time,
180
- #ifdef HAVE_ST_E_STATS
181
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_maxrss),
182
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_ixrss),
183
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_idrss),
184
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_isrss),
185
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_minflt),
186
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_majflt),
187
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_nswap),
188
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_inblock),
189
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_oublock),
190
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_msgsnd),
191
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_msgrcv),
192
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_nsignals),
193
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_nvcsw),
194
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_nivcsw),
195
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_utime.tv_sec),
196
- LONG2NUM(procs[i].kp_eproc.e_stats.p_ru.ru_stime.tv_sec)
197
- #else
198
- Qnil, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil,
199
- Qnil, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil
200
- #endif
201
- );
202
- #else
203
- v_pstruct = rb_struct_new(
204
- sProcStruct,
205
- INT2FIX(procs[i].ki_pid),
206
- INT2FIX(procs[i].ki_ppid),
207
- INT2FIX(procs[i].ki_pgid),
208
- INT2FIX(procs[i].ki_ruid),
209
- INT2FIX(procs[i].ki_rgid),
210
- rb_str_new2(procs[i].ki_ocomm),
211
- rb_str_new2(state),
212
- rb_float_new(procs[i].ki_pctcpu),
213
- INT2FIX(procs[i].ki_oncpu),
214
- v_tty_num,
215
- v_tty_dev,
216
- rb_str_new2(procs[i].ki_wmesg),
217
- INT2FIX(procs[i].ki_runtime/1000000),
218
- INT2FIX(procs[i].ki_pri.pri_level),
219
- INT2FIX(procs[i].ki_pri.pri_user),
220
- INT2FIX(procs[i].ki_nice),
221
- rb_str_new2(cmdline),
222
- v_start_time,
223
- Qnil, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil,
224
- Qnil, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil
225
- );
226
- #endif
227
-
228
- OBJ_FREEZE(v_pstruct); // Read-only data
229
-
230
- if(rb_block_given_p())
231
- rb_yield(v_pstruct);
232
- else
233
- rb_ary_push(v_array, v_pstruct);
234
- }
235
-
236
- if(kd)
237
- kvm_close(kd);
238
-
239
- if(!NIL_P(v_pid))
240
- return v_pstruct;
241
-
242
- return v_array; // Nil if block given
243
- }
244
-
245
- /*
246
- * call-seq:
247
- * ProcTable.fields
248
- *
249
- * Returns an array of fields that each ProcTableStruct will contain. This
250
- * may be useful if you want to know in advance what fields are available
251
- * without having to perform at least one read of the /proc table.
252
- */
253
- static VALUE pt_fields(VALUE klass){
254
- VALUE v_array = rb_ary_new();
255
- int size = sizeof(fields) / sizeof(fields[0]);
256
- int i;
257
-
258
- for(i = 0; i < size; i++)
259
- rb_ary_push(v_array, rb_str_new2(fields[i]));
260
-
261
- return v_array;
262
- }
263
-
264
- /*
265
- * A Ruby interface for gathering process table information.
266
- */
267
- void Init_proctable(){
268
- VALUE mSys, cProcTable;
269
-
270
- /* The Sys module serves as a namespace only */
271
- mSys = rb_define_module("Sys");
272
-
273
- /* The ProcTable class encapsulates process table information */
274
- cProcTable = rb_define_class_under(mSys, "ProcTable", rb_cObject);
275
-
276
- /* The error typically raised if any of the ProcTable methods fail */
277
- cProcTableError = rb_define_class_under(cProcTable, "Error", rb_eStandardError);
278
-
279
- /* Singleton Methods */
280
-
281
- rb_define_singleton_method(cProcTable, "ps", pt_ps, -1);
282
- rb_define_singleton_method(cProcTable, "fields", pt_fields, 0);
283
-
284
- /* There is no constructor */
285
- rb_funcall(cProcTable, rb_intern("private_class_method"), 1, ID2SYM(rb_intern("new")));
286
-
287
- /* Constants */
288
-
289
- /* 0.9.3: The version of the sys-proctable library */
290
- rb_define_const(cProcTable, "VERSION", rb_str_new2(SYS_PROCTABLE_VERSION));
291
-
292
- /* Structures */
293
-
294
- sProcStruct = rb_struct_define("ProcTableStruct","pid","ppid","pgid","ruid",
295
- "rgid","comm","state","pctcpu","oncpu","ttynum","ttydev","wmesg",
296
- "time", "priority","usrpri","nice","cmdline","start",
297
- "maxrss","ixrss","idrss","isrss","minflt","majflt","nswap",
298
- "inblock","oublock","msgsnd","msgrcv","nsignals","nvcsw","nivcsw",
299
- "utime","stime", NULL
300
- );
301
- }