The Artima Developer Community
Sponsored Link

Ruby Buzz Forum
Hardcore Systems Programming on Solaris with Ruby

0 replies on 1 page.

Welcome Guest
  Sign In

Go back to the topic listing  Back to Topic List Click to reply to this topic  Reply to this Topic Click to search messages in this forum  Search Forum Click for a threaded view of the topic  Threaded View   
Previous Topic   Next Topic
Flat View: This topic has 0 replies on 1 page
Daniel Berger

Posts: 1383
Nickname: djberg96
Registered: Sep, 2004

Daniel Berger is a Ruby Programmer who also dabbles in C and Perl
Hardcore Systems Programming on Solaris with Ruby Posted: Aug 28, 2008 5:55 PM
Reply to this message Reply

This post originated from an RSS feed registered with Ruby Buzz by Daniel Berger.
Original Post: Hardcore Systems Programming on Solaris with Ruby
Feed Title: Testing 1,2,3...
Feed URL: http://djberg96.livejournal.com/data/rss
Feed Description: A blog on Ruby and other stuff.
Latest Ruby Buzz Posts
Latest Ruby Buzz Posts by Daniel Berger
Latest Posts From Testing 1,2,3...

Advertisement
There's a subtle bug in the sys-proctable library that inspired me to attempt rewrites for the various platforms in pure Ruby. I've decided the loss in speed is heavily outweighed by the ease of maintenance.

Unlike Linux, Solaris stores process information in a binary format under /proc/<pid>/psinfo. Having done lots of pure Ruby win32-api programming now, I've become accustomed to unraveling binary data.

There was one problem, however. Solaris stores command line arguments for any given process in a separate file, /proc/<pid>/as. This file is special sparse file, and you can't use a standard IO seek & read because you need to read without moving the file pointer. You have to use something like lseek or pread. Ruby supports neither.

So, I updated my io-extra library to wrap both pread and pwrite, and used that. While using my current C code as a guideline (printing out addresses mostly), I also discovered a bug in the C version. Ugh.

Anyway, here's the final solution, which I also posted to ruby-talk:
require 'io/extra'

# Mozilla on Solaris. Adjust pid as needed.
#
# ps -ef shows "/bin/ksh", "-p", and "/usr/sfw/bin/mozilla"
#
pid = 2253

# Unravel some info we need from the psinfo struct
psinfo = IO.read("/proc/#{pid}/psinfo")
pr_argc = psinfo[188, 4].unpack("L")[0]
pr_argv = psinfo[192, 4].unpack("L")[0]

# Second, get our initial address from /proc/<pid>/as
fd = File.open("/proc/#{pid}/as")
addr = IO.pread(fd.fileno, pr_argc * 4, pr_argv).unpack("L")[0]

# Third, get each command argument, incrementing the address as
# needed. I've hard coded the read limit at 128. Adjust as needed.
0.upto(pr_argc - 1){ |i|
   data = IO.pread(fd.fileno, 128, addr)
   addr += data.length + 1 # Add 1 for the space
   p data
}

# Finally, close our file descriptor
fd.close 

Read: Hardcore Systems Programming on Solaris with Ruby

Topic: Rspec-rails mock_model helper for the RR test double framework Previous Topic   Next Topic Topic: DNC Event Map

Sponsored Links



Google
  Web Artima.com   

Copyright © 1996-2019 Artima, Inc. All Rights Reserved. - Privacy Policy - Terms of Use