Class: PosixPsutil::Process
- Inherits:
-
Object
- Object
- PosixPsutil::Process
- Includes:
- POSIX
- Defined in:
- lib/posixpsutil/process.rb
Overview
Warning: There is already a Process module in ruby, so don’t confuse it with this PosixPsutil::Process. And take care of ‘include PosixPsutil`, unless you have clearly considered about it.
Constant Summary collapse
- @@pmap =
{}
- @@total_phymem =
nil
Instance Attribute Summary collapse
-
#identity ⇒ Object
readonly
Returns the value of attribute identity.
-
#pid ⇒ Object
readonly
Returns the value of attribute pid.
Class Method Summary collapse
-
.pid_exists(pid) ⇒ Object
Return true if given PID exists in the current process list.
-
.pids ⇒ Object
Return an Array of current running PIDs.
-
.process_iter ⇒ Object
Like self.processes(), but return next Process instance in each iteration.
-
.processes ⇒ Object
Return all Process instances for all running processes.
Instance Method Summary collapse
- #!=(other) ⇒ Object
-
#==(other) ⇒ Object
(also: #eql?)
Test for equality with another Process object based on PID and creation time.
-
#children(recursive = false) ⇒ Object
Return the children of this process as a list of Process instances, pre-emptively checking whether PID has been reused.
-
#cmdline ⇒ Object
The command line this process has been called with.
-
#connections(interface = :inet) ⇒ Object
Return connections opened by process as a list of #<OpenStruct fd, family, type, laddr, raddr, status> The ‘kind’ parameter filters for connections that match the following criteria:.
-
#cpu_affinity(cpus = nil) ⇒ Object
Get or set process CPU affinity.
-
#cpu_percent(interval = nil) ⇒ Object
Return a float representing the current process CPU utilization as a percentage.
-
#cpu_times ⇒ Object
Return a #<OpenStruct user, system> representing the accumulated process time, in seconds.
-
#create_time ⇒ Object
The process creation time as a floating point number expressed in seconds since the epoch, in UTC.
-
#cwd ⇒ Object
Process current working directory as an absolute path.
-
#exe ⇒ Object
The process executable as an absolute path.
-
#gids ⇒ Object
Return process GIDs as #<OpenStruct real, effective, saved>.
-
#initialize(pid = nil) ⇒ Process
constructor
initialize a Process instance with pid, if not pid given, initialize it with current process’s pid.
-
#inspect ⇒ Object
Return a printable version of Process instance’s description.
-
#io_counters ⇒ Object
Linux, BSD only.
-
#ionice(ioclass = nil, value = nil) ⇒ Object
Linux only.
-
#is_running ⇒ Object
Return if this process is running.
-
#kill ⇒ Object
Kill the current process with SIGKILL pre-emptively checking whether PID has been reused.
-
#memory_info ⇒ Object
Return an OpenStruct representing RSS (Resident Set Size) and VMS (Virtual Memory Size) in bytes.
-
#memory_info_ex ⇒ Object
Return an OpenStruct with variable fields depending on the platform representing extended memory information about this process.
-
#memory_maps(grouped = true) ⇒ Object
If ‘grouped’ is false every mapped region is shown as a single entity and the namedtuple will also include the mapped region’s address space (‘addr’) and permission set (‘perms’).
-
#memory_percent ⇒ Object
Compare physical system memory to process resident memory (RSS) and calculate process memory utilization as a percentage.
-
#name ⇒ Object
The process name.
-
#nice ⇒ Object
Get process niceness (priority).
-
#nice=(value) ⇒ Object
Set process niceness.
-
#num_ctx_switches ⇒ Object
Return the number of voluntary and involuntary context switches performed by this process.
-
#num_fds ⇒ Object
Return the number of file descriptors opened by this process.
-
#num_threads ⇒ Object
Return the number of threads used by this process.
-
#open_files ⇒ Object
Return regular files opened by process as a list of <#OpenStruct path, fd> including the absolute file name and file descriptor number.
-
#parent ⇒ Object
Return the parent process as a Process object pre-emptively checking whether PID has been reused.
-
#ppid ⇒ Object
Return the parent pid of the process.
-
#resume ⇒ Object
Resume process execution with SIGCONT pre-emptively checking whether PID has been reused.
-
#rlimit(resource, limits = nil) ⇒ Object
Get or set process resource limits as a :hard Hash.
-
#send_signal(sig) ⇒ Object
Send a signal to process pre-emptively checking whether PID has been reused (see signal module constants) .
-
#status ⇒ Object
The process current status as a STATUS_* constant.
-
#suspend ⇒ Object
Suspend process execution with SIGSTOP pre-emptively checking whether PID has been reused.
-
#terminal ⇒ Object
The terminal associated with this process, if any, else nil.
-
#terminate ⇒ Object
Terminate process execution with SIGTERM pre-emptively checking whether PID has been reused.
-
#threads ⇒ Object
Return threads opened by process as a list of #<OpenStruct id, user_time, system_time> representing thread id and thread CPU times (user/system).
-
#time_used ⇒ Object
Return the wall time cost by process, measured in seconds.
-
#to_hash(given_attrs = nil, default = {}) ⇒ Object
‘default’ is the value which gets assigned in case AccessDenied exception is raised when retrieving that particular process information.
-
#to_s ⇒ Object
Return description of Process instance.
-
#uids ⇒ Object
Return process UIDs as #<OpenStruct real, effective, saved>.
-
#username ⇒ Object
The name of the user that owns the process.
-
#wait(timeout = nil) ⇒ Object
Waiting until process does not existed any more.
Methods included from POSIX
Constructor Details
#initialize(pid = nil) ⇒ Process
initialize a Process instance with pid, if not pid given, initialize it with current process’s pid.
136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 |
# File 'lib/posixpsutil/process.rb', line 136 def initialize(pid=nil) pid = ::Process.pid unless pid @pid = pid raise ArgumentError.new("pid must be a positive integer (got #{@pid})") if @pid <= 0 @name = nil @exe = nil @create_time = nil @gone = false @proc = PlatformSpecificProcess.new(@pid) # for cpu_percent @last_sys_cpu_times = nil @last_proc_cpu_times = nil begin create_time rescue AccessDenied # we should never get here as AFAIK we're able to get # process creation time on all platforms even as a # limited user rescue NoSuchProcess msg = "no process found with pid #{@pid}" raise NoSuchProcess.new(pid:@pid, msg:msg) end # This part is supposed to indentify a Process instance # univocally over time (the PID alone is not enough as # it might refer to a process whose PID has been reused). # This will be used later in == and is_running(). @identity = [@pid, @create_time] end |
Instance Attribute Details
#identity ⇒ Object (readonly)
Returns the value of attribute identity.
59 60 61 |
# File 'lib/posixpsutil/process.rb', line 59 def identity @identity end |
#pid ⇒ Object (readonly)
Returns the value of attribute pid.
60 61 62 |
# File 'lib/posixpsutil/process.rb', line 60 def pid @pid end |
Class Method Details
.pid_exists(pid) ⇒ Object
Return true if given PID exists in the current process list. This is faster than doing “pid in psutil.pids()” and should be preferred.
72 73 74 |
# File 'lib/posixpsutil/process.rb', line 72 def self.pid_exists(pid) POSIX::pid_exists(pid) end |
.pids ⇒ Object
Return an Array of current running PIDs.
65 66 67 |
# File 'lib/posixpsutil/process.rb', line 65 def self.pids PlatformSpecificProcess.pids() end |
.process_iter ⇒ Object
Like self.processes(), but return next Process instance in each iteration. To imitate Python’s iterator, use Enumerator to implement this method, which means it will raise StopIteration when it reaches the end.
114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 |
# File 'lib/posixpsutil/process.rb', line 114 def self.process_iter processes = [] pids().each do |pid| begin unless @@pmap.key?(pid) && @@pmap[pid].is_running p = Process.new(pid) @@pmap[p.pid] = p end processes.push @@pmap[pid] rescue NoSuchProcess @@pmap.delete(pid) rescue AccessDenied next end end processes.to_enum end |
.processes ⇒ Object
Return all Process instances for all running processes.
Every new Process instance is only created once and then cached into an internal table which is updated every time this is used.
Cached Process instances are checked for identity so that you’re safe in case a PID has been reused by another process, in which case the cached instance is updated.
88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 |
# File 'lib/posixpsutil/process.rb', line 88 def self.processes pre_pids = @@pmap.keys cur_pids = pids() gone_pids = pre_pids - cur_pids gone_pids.each { |pid| @@pmap.delete(pid) } cur_pids.each do |pid| begin unless @@pmap.key?(pid) && @@pmap[pid].is_running p = Process.new(pid) @@pmap[p.pid] = p end rescue NoSuchProcess @@pmap.delete(pid) rescue AccessDenied # Process creation time can't be determined hence there's # no way to tell whether the pid of the cached process next end end @@pmap.values end |
Instance Method Details
#!=(other) ⇒ Object
189 190 191 |
# File 'lib/posixpsutil/process.rb', line 189 def !=(other) return !(self == other) end |
#==(other) ⇒ Object Also known as: eql?
Test for equality with another Process object based on PID and creation time.
184 185 186 |
# File 'lib/posixpsutil/process.rb', line 184 def ==(other) return self.class == other.class && @identity == other.identity end |
#children(recursive = false) ⇒ Object
Return the children of this process as a list of Process instances, pre-emptively checking whether PID has been reused. If recursive is true return all the parent descendants.
Example (A == this process):
A
567 568 569 570 571 572 573 574 575 576 577 578 579 580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 |
# File 'lib/posixpsutil/process.rb', line 567 def children(recursive = false) ret = [] if recursive # construct a hash where 'values'(an Array) are all the processes # having 'key' as their parent table = {} self.class.processes.each do |p| begin ppid = p.ppid (table.key? ppid)? table[ppid].push(p) : table[ppid] = [p] rescue NoSuchProcess next end end # At this point we have a mapping table where table[self.pid] # are the current process' children. # Below, we look for all descendants recursively, similarly # to a recursive function call. checkpids = [@pid] checkpids.each do |pid| next unless table.key? pid table[pid].each do |child| begin # if child happens to be older than its parent, # it means child's PID has been reused intime = (create_time() <= child.create_time()) rescue NoSuchProcess next end if intime ret.push(child) checkpids.push(child.pid) unless checkpids.include?(child.pid) end end end else self.class.processes().each do |p| begin ret.push(p) if p.ppid == @pid && create_time() <= p.create_time() rescue NoSuchProcess next end end end ret end |
#cmdline ⇒ Object
The command line this process has been called with. An array will be returned
330 331 332 |
# File 'lib/posixpsutil/process.rb', line 330 def cmdline @proc.cmdline() end |
#connections(interface = :inet) ⇒ Object
Return connections opened by process as a list of #<OpenStruct fd, family, type, laddr, raddr, status> The ‘kind’ parameter filters for connections that match the following criteria:
Kind Value Connections using :inet IPv4 and IPv6 :inet4 IPv4 :inet6 IPv6 :tcp TCP :tcp4 TCP over IPv4 :tcp6 TCP over IPv6 :udp UDP :udp4 UDP over IPv4 :udp6 UDP over IPv6 :unix UNIX socket (both UDP and TCP protocols) :all the sum of all the possible families and protocols
773 774 775 |
# File 'lib/posixpsutil/process.rb', line 773 def connections(interface = :inet) @proc.connections(interface) end |
#cpu_affinity(cpus = nil) ⇒ Object
Get or set process CPU affinity. If specified ‘cpus’ must be a list of CPUs for which you want to set the affinity (e.g. [0, 1]).
If ‘cpus’ is not an Array, an ArgumentError will be raised, if the length of ‘cpus’ larger than the number of CPUs, the remain will be ignore.
516 517 518 519 520 521 522 523 524 |
# File 'lib/posixpsutil/process.rb', line 516 def cpu_affinity(cpus=nil) if cpus.nil? @proc.cpu_affinity elsif cpus.is_a?(Array) @proc.cpu_affinity=(cpus) else raise ArgumentError.new("cpus must be an Array, got #{cpus}") end end |
#cpu_percent(interval = nil) ⇒ Object
Return a float representing the current process CPU utilization as a percentage.
When interval is <= 0.0 or nil (default) compares process times to system CPU times elapsed since last call, returning immediately (non-blocking). That means that the first time this is called it will return a meaningful 0.0 value.
When interval is > 0.0 compares process times to system CPU times elapsed before and after the interval.
In this case is recommended for accuracy that this function be called with at least 0.1 seconds between calls.
Examples:
require 'posixpsutil'
p = PosixPsutil::Process.new(Process.pid)
# blocking
p.cpu_percent(1)
# 2.0
# non-blocking (percentage since last call)
p.cpu_percent
# 2.9
p = PosixPsutil::Process.new(4527)
# first called
p.cpu_percent
# 0.0
# second called
p.cpu_percent
# 0.5
654 655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 |
# File 'lib/posixpsutil/process.rb', line 654 def cpu_percent(interval = nil) blocking = (interval && interval > 0.0) num_cpus = CPU.cpu_count() timer = proc { Time.now.to_f * num_cpus } if blocking st1 = timer.call pt1 = @proc.cpu_times sleep interval st2 = timer.call pt2 = @proc.cpu_times else st1 = @last_sys_cpu_times pt1 = @last_proc_cpu_times st2 = timer.call pt2 = @proc.cpu_times # first called if st1.nil? || pt1.nil? @last_sys_cpu_times = st2 @last_proc_cpu_times = pt2 return 0.0 end end delta_proc = (pt2.user - pt1.user) + (pt2.system - pt1.system) delta_time = st2 - st1 # reset values for next call in case of interval == None @last_sys_cpu_times = st2 @last_proc_cpu_times = pt2 begin # The utilization split between all CPUs. # Note: a percentage > 100 is legitimate as it can result # from a process with multiple threads running on different # CPU cores, see: # http://stackoverflow.com/questions/1032357 # https://github.com/giampaolo/psutil/issues/474 overall_percent = ((delta_proc / delta_time) * 100) * num_cpus return overall_percent.round(1) rescue ZeroDivisionError # interval was too low return 0.0 end end |
#cpu_times ⇒ Object
Return a #<OpenStruct user, system> representing the accumulated process time, in seconds.
351 352 353 |
# File 'lib/posixpsutil/process.rb', line 351 def cpu_times @proc.cpu_times end |
#create_time ⇒ Object
The process creation time as a floating point number expressed in seconds since the epoch, in UTC. The return value is cached after first call.
358 359 360 361 362 363 |
# File 'lib/posixpsutil/process.rb', line 358 def create_time if @create_time.nil? @create_time = @proc.create_time end @create_time end |
#cwd ⇒ Object
Process current working directory as an absolute path.
371 372 373 |
# File 'lib/posixpsutil/process.rb', line 371 def cwd @proc.cwd end |
#exe ⇒ Object
The process executable as an absolute path. May also be an empty string. The return value is cached after first call.
303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 |
# File 'lib/posixpsutil/process.rb', line 303 def exe if !@exe begin @exe = @proc.exe() rescue AccessDenied => e @exe = '' fallback = e end if @exe == '' cmdline = self.cmdline() if cmdline exe = cmdline[0] if File.exists?(exe) && File.realpath == exe \ && File.stat(exe).executable? @exe = exe end else raise fallback if fallback end end end @exe end |
#gids ⇒ Object
Return process GIDs as #<OpenStruct real, effective, saved>
396 397 398 |
# File 'lib/posixpsutil/process.rb', line 396 def gids @proc.gids end |
#inspect ⇒ Object
Return a printable version of Process instance’s description.
178 179 180 |
# File 'lib/posixpsutil/process.rb', line 178 def inspect self.to_s.inspect end |
#io_counters ⇒ Object
Linux, BSD only
Return process I/O statistics as a #<OpenStruct read_count, write_count, read_bytes, write_bytes>
Those are the number of read/write calls performed and the amount of bytes read and written by the process.
429 430 431 |
# File 'lib/posixpsutil/process.rb', line 429 def io_counters @proc.io_counters end |
#ionice(ioclass = nil, value = nil) ⇒ Object
Linux only
Get or set process I/O niceness (priority).
On Linux ‘ioclass’ is one of the IOPRIO_CLASS_* constants. ‘value’ is a number which goes from 0 to 7. The higher the value, the lower the I/O priority of the process. ‘man ionice` for further info
You can use symbols or CONSTANTS as ioclass argument. For example, ‘p.ioclass(:be, 4)` or `p.ioclass(PosixPsutil::IOPRIO_CLASS_BE, 4)`
-
IOPRIO_CLASS_NONE :none => 0
-
IOPRIO_CLASS_RT :rt => 1
-
IOPRIO_CLASS_BE :be => 2
-
IOPRIO_CLASS_IDLE :idle => 3
453 454 455 456 457 458 459 460 461 |
# File 'lib/posixpsutil/process.rb', line 453 def ionice(ioclass=nil, value=nil) if ioclass.nil? raise ArgumentError.new("'ioclass' must be specified") if value return @proc.ionice else # If the value is nil, a reasonable value will be assigned return @proc.set_ionice(ioclass, value) end end |
#is_running ⇒ Object
Return if this process is running. It also checks if PID has been reused by another process in which case return false.
263 264 265 266 267 268 269 270 271 |
# File 'lib/posixpsutil/process.rb', line 263 def is_running return false if @gone begin return self == Process.new(@pid) rescue NoSuchProcess @gone = true return false end end |
#kill ⇒ Object
Kill the current process with SIGKILL pre-emptively checking whether PID has been reused.
It is not an alias_method of send_signal
825 826 827 |
# File 'lib/posixpsutil/process.rb', line 825 def kill send_signal('KILL') end |
#memory_info ⇒ Object
Return an OpenStruct representing RSS (Resident Set Size) and VMS (Virtual Memory Size) in bytes.
700 701 702 |
# File 'lib/posixpsutil/process.rb', line 700 def memory_info @proc.memory_info end |
#memory_info_ex ⇒ Object
Return an OpenStruct with variable fields depending on the platform representing extended memory information about this process. All numbers are expressed in bytes.
707 708 709 |
# File 'lib/posixpsutil/process.rb', line 707 def memory_info_ex @proc.memory_info_ex end |
#memory_maps(grouped = true) ⇒ Object
If ‘grouped’ is false every mapped region is shown as a single entity and the namedtuple will also include the mapped region’s address space (‘addr’) and permission set (‘perms’).
733 734 735 736 737 738 739 740 741 742 743 744 745 746 747 |
# File 'lib/posixpsutil/process.rb', line 733 def memory_maps(grouped = true) maps = @proc.memory_maps if grouped d = {} maps.each do |region| path = region[2] nums = region[3..-1] (d[path].nil? ) ? d[path] = nums : d[path].each_index {|i| d[path][i] += nums[i]} end @proc.pmmap_grouped(d) else @proc.pmmap_ext(maps) end end |
#memory_percent ⇒ Object
Compare physical system memory to process resident memory (RSS) and calculate process memory utilization as a percentage.
714 715 716 717 718 719 720 721 722 |
# File 'lib/posixpsutil/process.rb', line 714 def memory_percent rss = @proc.memory_info.rss @@total_phymem = Memory.virtual_memory.total if @@total_phymem.nil? begin return (rss / @@total_phymem.to_f * 100).round(2) rescue ZeroDivisionError return 0.0 end end |
#name ⇒ Object
The process name. The return value is cached after first call.
281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 |
# File 'lib/posixpsutil/process.rb', line 281 def name unless @name @name = @proc.name() if @name.length >= 15 begin # return an Array represented cmdline arguments( may be [] ) cmdline = cmdline() rescue AccessDenied cmdline = [] end if cmdline != [] extended_name = File.basename(cmdline[0]) @name = extended_name if extended_name.start_with?(@name) end end end @name end |
#nice ⇒ Object
Get process niceness (priority).
376 377 378 |
# File 'lib/posixpsutil/process.rb', line 376 def nice @proc.nice end |
#nice=(value) ⇒ Object
Set process niceness. Niceness values range from -20 (most favorable to the process) to 19 (least favorable to the process) on Linux.
383 384 385 386 387 388 |
# File 'lib/posixpsutil/process.rb', line 383 def nice=(value) raise NoSuchProcess.new(pid:@pid) unless is_running() # valid niceness range is system dependency, # so let each platform specific implemention handle the input @proc.nice = value end |
#num_ctx_switches ⇒ Object
Return the number of voluntary and involuntary context switches performed by this process.
529 530 531 |
# File 'lib/posixpsutil/process.rb', line 529 def num_ctx_switches @proc.num_ctx_switches end |
#num_fds ⇒ Object
Return the number of file descriptors opened by this process
406 407 408 |
# File 'lib/posixpsutil/process.rb', line 406 def num_fds @proc.num_fds end |
#num_threads ⇒ Object
Return the number of threads used by this process.
534 535 536 |
# File 'lib/posixpsutil/process.rb', line 534 def num_threads @proc.num_threads end |
#open_files ⇒ Object
Return regular files opened by process as a list of <#OpenStruct path, fd> including the absolute file name and file descriptor number.
752 753 754 |
# File 'lib/posixpsutil/process.rb', line 752 def open_files @proc.open_files end |
#parent ⇒ Object
Return the parent process as a Process object pre-emptively checking whether PID has been reused. If no parent is known return nil.
247 248 249 250 251 252 253 254 255 256 257 258 |
# File 'lib/posixpsutil/process.rb', line 247 def parent ppid = ppid() if ppid begin parent = Process.new ppid return parent if parent.create_time() <= create_time() rescue NoSuchProcess # ignore ... end end return nil end |
#ppid ⇒ Object
Return the parent pid of the process.
276 277 278 |
# File 'lib/posixpsutil/process.rb', line 276 def ppid @proc.ppid end |
#resume ⇒ Object
Resume process execution with SIGCONT pre-emptively checking whether PID has been reused.
811 812 813 |
# File 'lib/posixpsutil/process.rb', line 811 def resume send_signal('CONT') end |
#rlimit(resource, limits = nil) ⇒ Object
Get or set process resource limits as a :hard Hash.
‘resource’ is one of the RLIMIT_* constants. Unlike other API, ‘limits’ is supposed to be a :hard Hash, instead of an OpenStruct. Since using Hash as input is more common than using OpenStruct (and more handy, too).
‘man prlimit` for further info. And see bits/resource.h for the detail about resource.
You can use symbols or CONSTANTS as resource argument. For example:
limits = {:soft => 1024, :hard => 4096}
p.rlimit(PosixPsutil::RLIMIT_NOFILE, limits)
# or
p.rlimit(:nofile, limits)
-
RLIMIT_CPU :cpu => 0
-
RLIMIT_FSIZE :fsize => 1
-
RLIMIT_DATA :data => 2
-
RLIMIT_STACK :stack => 3
-
RLIMIT_CORE :core => 4
-
RLIMIT_RSS :rss => 5
-
RLIMIT_NPROC :nproc => 6
-
RLIMIT_NOFILE :nofile => 7
-
RLIMIT_MEMLOCK :memlock => 8
-
RLIMIT_AS :as => 9
-
RLIMIT_LOCKS :locks => 10
-
RLIMIT_SIGPENDING :sigpending => 11
-
RLIMIT_MSGQUEUE :msgqueue => 12
-
RLIMIT_NICE :nice => 13
-
RLIMIT_RTPRIO :rtprio => 14
-
RLIMIT_RTTIME :rttime => 15
-
RLIMIT_NLIMITS :nlimits => 16
501 502 503 |
# File 'lib/posixpsutil/process.rb', line 501 def rlimit(resource, limits=nil) @proc.rlimit(resource, limits) end |
#send_signal(sig) ⇒ Object
Send a signal to process pre-emptively checking whether PID has been reused (see signal module constants) .
signal may be an integer signal number or a POSIX signal name (either with or without a SIG prefix). For example, ‘SIGSTOP’/‘STOP’/19 all means the signal SIGSTOP
According to Ruby doc, > If signal is negative (or starts with a minus sign), > kills process groups instead of processes
Currently I consider it as a feature and will not change this behaviour
789 790 791 792 793 794 795 796 797 798 799 800 801 |
# File 'lib/posixpsutil/process.rb', line 789 def send_signal(sig) begin # according to "man 2 kill" , PID 0 refers to # 'every process in the process group of the calling process' # Luckily, @pid is >= 0 ::Process.kill(sig, @pid) rescue Errno::ESRCH @gone = true raise NoSuchProcess(@pid, @name) rescue Errno::EPERM raise AccessDenied(@pid, @name) end end |
#status ⇒ Object
The process current status as a STATUS_* constant.
335 336 337 |
# File 'lib/posixpsutil/process.rb', line 335 def status @proc.status() end |
#suspend ⇒ Object
Suspend process execution with SIGSTOP pre-emptively checking whether PID has been reused.
805 806 807 |
# File 'lib/posixpsutil/process.rb', line 805 def suspend send_signal('STOP') end |
#terminal ⇒ Object
The terminal associated with this process, if any, else nil.
401 402 403 |
# File 'lib/posixpsutil/process.rb', line 401 def terminal @proc.terminal end |
#terminate ⇒ Object
Terminate process execution with SIGTERM pre-emptively checking whether PID has been reused.
817 818 819 |
# File 'lib/posixpsutil/process.rb', line 817 def terminate send_signal('TERM') end |
#threads ⇒ Object
Return threads opened by process as a list of #<OpenStruct id, user_time, system_time> representing thread id and thread CPU times (user/system).
541 542 543 |
# File 'lib/posixpsutil/process.rb', line 541 def threads @proc.threads end |
#time_used ⇒ Object
Return the wall time cost by process, measured in seconds
366 367 368 |
# File 'lib/posixpsutil/process.rb', line 366 def time_used @proc.time_used end |
#to_hash(given_attrs = nil, default = {}) ⇒ Object
‘default’ is the value which gets assigned in case AccessDenied exception is raised when retrieving that particular process information.
207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 |
# File 'lib/posixpsutil/process.rb', line 207 def to_hash(given_attrs = nil, default = {}) # psutil defines some excluded methods, they won't be accessed via # this method. # # psutil want to warn us that the process with given pid may gone, # as the comment at the head of the class says. excluded_names = [ :identity, :to_s, :inspect, :==, :eql?, :!=, :to_hash, :parent, :is_running, :children, :rlimit, :send_signal, :kill, :terminate, :resume, :suspend, :wait ] respond_to_methods = self.public_methods(false) included_names = respond_to_methods - excluded_names ret = {} attrs = (given_attrs ? given_attrs : included_names) attrs.each do |attr| next if !attr.is_a?(Symbol) || attr.to_s.end_with?('=') begin # filter unsafe methods if respond_to_methods.include?(attr) ret[attr] = method(attr).call() else # in case of not implemented functionality (may happen # on old or exotic systems) we want to crash only if # the user explicitly asked for that particular attr raise NotImplementedError if given_attrs ret[attr] = default[attr] if default.key? attr end rescue AccessDenied ret[attr] = default[attr] if default.key? attr end end ret end |
#to_s ⇒ Object
Return description of Process instance.
167 168 169 170 171 172 173 174 175 |
# File 'lib/posixpsutil/process.rb', line 167 def to_s begin return "(pid=#{@pid}, name=#{name()})" rescue NoSuchProcess return "(pid=#{@pid} (terminated))" rescue AccessDenied return "(pid=#{@pid})" end end |
#uids ⇒ Object
Return process UIDs as #<OpenStruct real, effective, saved>
391 392 393 |
# File 'lib/posixpsutil/process.rb', line 391 def uids @proc.uids end |
#username ⇒ Object
The name of the user that owns the process.
340 341 342 343 344 345 346 347 |
# File 'lib/posixpsutil/process.rb', line 340 def username real_uid = uids[:real] begin return Etc::getpwuid(real_uid).name rescue ArgumentError return real_uid.to_s end end |
#wait(timeout = nil) ⇒ Object
Waiting until process does not existed any more. Raise Timeout::Error if time out while waiting.
412 413 414 415 416 417 418 419 |
# File 'lib/posixpsutil/process.rb', line 412 def wait(timeout = nil) if timeout && timeout < 0 raise ArgumentError.new("timeout must be a positive integer") end return wait_pid(@pid, timeout) # maybe raise Timeout::Error, need not to convert it currently #rescue Timeout::Error end |