D
Daniel Berger
Hi all,
Ruby 1.8.6
Solaris 10
I'm trying to get process information on a Solaris using pure Ruby.
For the basic information, this is fairly straightforward, as I read
out of /proc/<pid>/psinfo.
However, where I'm having trouble is getting the command line
arguments out of /proc/<pid>/as. Basically, I need to know how to
unravel the data I'm reading into a human readable string.
Here's some sample code:
# sunos.rb
module Sys
class ProcTable
def self.ps(pid = nil)
Dir.foreach("/proc") do |file|
next if file =~ /\D/
next if pid && file.to_i != pid
psinfo = IO.read("/proc/#{file}/psinfo")
pid = psinfo[8,4].unpack("L")[0]
puts "PID: #{pid}"
argc = psinfo[188,4].unpack("L")[0] # pr_argc
addr = psinfo[192,4].unpack("L")[0] # pr_argv
size = argc * 4 # 4 is the sizeof(caddr32_t)
asinfo = IO.read("/proc/#{file}/as", size, addr)
# How do I unravel asinfo?
p asinfo
end
end
end
end
if $0 == __FILE__
include Sys
ProcTable.ps(2764) # or whatever pid you prefer
end
The C code I'm trying to simulate, which I pulled from a post by Roger
Faulkner on comp.unix.questions, looks something like this:
addr_args = p.pr_argv; /* from the psinfo struct */
arg_count = p.pr_argc; /* from the psinfo struct */
if((fd = open(as_file, O_RDONLY)) < 0){
/* Do nothing - you can only get info on processes you rights to */
}
else
{
arg_vec = malloc(arg_count * sizeof(uintptr_t));
(void)pread(fd, arg_vec, arg_count * sizeof (uintptr_t),
addr_args);
arg_len = 16;
arg = malloc(arg_len+1);
for(i = 0; i < arg_count; i++) {
if(pread(fd, arg, arg_len, arg_vec) < 0)
continue;
arg[arg_len] = '\0';
if(strlen(arg) == arg_len){
arg_len *= 2;
arg = realloc(arg, arg_len + 1);
i--;
continue;
}
rb_ary_push(v_cmd_array, rb_str_new2(arg));
}
free(arg);
free(arg_vec);
}
close(fd);
Any ideas how to get the string(s) I need out of /proc/<pid>/as ?
Thanks,
Dan
Ruby 1.8.6
Solaris 10
I'm trying to get process information on a Solaris using pure Ruby.
For the basic information, this is fairly straightforward, as I read
out of /proc/<pid>/psinfo.
However, where I'm having trouble is getting the command line
arguments out of /proc/<pid>/as. Basically, I need to know how to
unravel the data I'm reading into a human readable string.
Here's some sample code:
# sunos.rb
module Sys
class ProcTable
def self.ps(pid = nil)
Dir.foreach("/proc") do |file|
next if file =~ /\D/
next if pid && file.to_i != pid
psinfo = IO.read("/proc/#{file}/psinfo")
pid = psinfo[8,4].unpack("L")[0]
puts "PID: #{pid}"
argc = psinfo[188,4].unpack("L")[0] # pr_argc
addr = psinfo[192,4].unpack("L")[0] # pr_argv
size = argc * 4 # 4 is the sizeof(caddr32_t)
asinfo = IO.read("/proc/#{file}/as", size, addr)
# How do I unravel asinfo?
p asinfo
end
end
end
end
if $0 == __FILE__
include Sys
ProcTable.ps(2764) # or whatever pid you prefer
end
The C code I'm trying to simulate, which I pulled from a post by Roger
Faulkner on comp.unix.questions, looks something like this:
addr_args = p.pr_argv; /* from the psinfo struct */
arg_count = p.pr_argc; /* from the psinfo struct */
if((fd = open(as_file, O_RDONLY)) < 0){
/* Do nothing - you can only get info on processes you rights to */
}
else
{
arg_vec = malloc(arg_count * sizeof(uintptr_t));
(void)pread(fd, arg_vec, arg_count * sizeof (uintptr_t),
addr_args);
arg_len = 16;
arg = malloc(arg_len+1);
for(i = 0; i < arg_count; i++) {
if(pread(fd, arg, arg_len, arg_vec) < 0)
continue;
arg[arg_len] = '\0';
if(strlen(arg) == arg_len){
arg_len *= 2;
arg = realloc(arg, arg_len + 1);
i--;
continue;
}
rb_ary_push(v_cmd_array, rb_str_new2(arg));
}
free(arg);
free(arg_vec);
}
close(fd);
Any ideas how to get the string(s) I need out of /proc/<pid>/as ?
Thanks,
Dan