Super User Can't Change UID?

Why would the super user not be able to switch UID’s?

$ sudo ruby -r etc -e ‘Process.uid = Etc.getpwnam(“james”).uid’
Password:
-e:1:in `uid=’: Operation not permitted (Errno::EPERM)
from -e:1

Tips of TFM I should go R are welcome. :slight_smile:

James Edward G. II

This works on my gentoo without any problem. Try to became root and
try to run to see if it’s another problem.

2009/1/27 James G. [email protected]:

On Jan 27, 2009, at 5:21 PM, Michel B. wrote:

This works on my gentoo without any problem. Try to became root and
try to run to see if it’s another problem.

It doesn’t seem to work for me that way either:

$ sudo sh
Password:
sh-3.2# ruby -r etc -e ‘Process.uid = Etc.getpwnam(“james”).uid’
-e:1:in `uid=’: Operation not permitted (Errno::EPERM)
from -e:1

James Edward G. II

On Jan 27, 2009, at 5:11 PM, James G. wrote:

Why would the super user not be able to switch UID’s?

$ sudo ruby -r etc -e ‘Process.uid = Etc.getpwnam(“james”).uid’
Password:
-e:1:in `uid=’: Operation not permitted (Errno::EPERM)
from -e:1

Another data point on this odd issue: Apple’s bundled Ruby (I’m on OS
X) works:

$ sudo /usr/bin/ruby -r etc -e ‘Process.uid =
Etc.getpwnam(“james”).uid’
Password:
$

It’s just the Ruby I built that fails. How could I have messed this
up in the build?

James Edward G. II

On Jan 27, 2009, at 6:45 PM, Rob B. wrote:

It works for me on Ubuntu and Mac OS X also.

Were you using Apple’s bundled Ruby or something you compiled?

James Edward G. II

On Jan 27, 2009, at 9:34 PM, James G. wrote:

On Jan 27, 2009, at 6:45 PM, Rob B. wrote:

It works for me on Ubuntu and Mac OS X also.

Were you using Apple’s bundled Ruby or something you compiled?

James Edward G. II

Apple’s /usr/bin/ruby. (I’d answered before I saw your
clarification.) I also just ran it fine with macruby.

$ sudo macruby -r etc -e ‘puts Process.pid,Process.uid; sleep 2;puts
“now”; Process.uid = Etc.getpwnam(“rab”).uid; puts Process.uid; sleep 2’
Password:
26951
0
now
501

I don’t suppose that really helps you much.

-Rob

Rob B. http://agileconsultingllc.com
[email protected]

On Jan 27, 2009, at 6:26 PM, James G. wrote:

-e:1:in `uid=': Operation not permitted (Errno::EPERM)
from -e:1

James Edward G. II

It works for me on Ubuntu and Mac OS X also.

-Rob

Rob B. http://agileconsultingllc.com
[email protected]

On Jan 27, 2009, at 7:06 PM, James G. wrote:

James Edward G. II

James Edward G. II

It fails for me on my self compiled ruby 1.8.6 on osx but the built
in ruby and my gentoo ruby works fine. No clue why.

-Ezra

James G. wrote:

Why would the super user not be able to switch UID’s?

$ sudo ruby -r etc -e ‘Process.uid = Etc.getpwnam(“james”).uid’
Password:
-e:1:in `uid=’: Operation not permitted (Errno::EPERM)
from -e:1

Tips of TFM I should go R are welcome. :slight_smile:

I seem to recall that setreuid() is busted on OS X, 10.4.x anyway. I
think it’s fixed in 10.5, but I can’t confirm.

I know this has come up before. Check the the ruby-core archives.

Regards,

Dan

James G. wrote:

X) works:

$ sudo /usr/bin/ruby -r etc -e ‘Process.uid = Etc.getpwnam(“james”).uid’
Password:
$

It’s just the Ruby I built that fails. How could I have messed this up
in the build?

Are you on 10.4.x?

If I had to guess, I’d bet Apple replaced setreuid() with seteuid(), but
that’s a guess.

I’ve never really understood the way OS X manages users. My own account
is not in /etc/passwd, but shows up in NetInfo.

Regards,

Dan

On Jan 27, 2009, at 11:18 PM, Daniel B. wrote:

James G. wrote:

Why would the super user not be able to switch UID’s?
$ sudo ruby -r etc -e ‘Process.uid = Etc.getpwnam(“james”).uid’
Password:
-e:1:in `uid=’: Operation not permitted (Errno::EPERM)
from -e:1
Tips of TFM I should go R are welcome. :slight_smile:

I seem to recall that setreuid() is busted on OS X, 10.4.x anyway. I
think it’s fixed in 10.5, but I can’t confirm.

I’m on Mac OS X 10.5.6.

I know this has come up before. Check the the ruby-core archives.

I did a few searches, but didn’t find a match. I did find old posts
about how Process.uid= can’t handle negative UID’s which is another
issue I’m fighting, but nothing about this issue.

On Jan 28, 2009, at 8:01 AM, Daniel B. wrote:

If I had to guess, I’d bet Apple replaced setreuid() with seteuid(),
but that’s a guess.

If that were the case, would it maybe be possible to switch users
using Apple’s alternate API?

Unfortunately, this issue is a big snag that’s preventing us from
shipping an application, so I’ve got to find some workaround. I’ve
considered trying to exec() my program adding su/sudo to switch the
user as a possible option. Would that work? I need to switch both
the user and group.

James Edward G. II

On Jan 27, 2009, at 9:00 PM, Rob B. wrote:

Apple’s /usr/bin/ruby. (I’d answered before I saw your
clarification.) I also just ran it fine with macruby.

It also seems to work in my locally compiled 1.9:

$ sudo ruby_dev -r etc -ve ‘Process.uid = Etc.getpwnam(“james”).uid’
Password:
ruby 1.9.1 (2008-12-30 patchlevel-0 revision 21203) [i386- darwin9.6.0]

James Edward G. II

On Jan 28, 2009, at 8:24 AM, James G. wrote:

I seem to recall that setreuid() is busted on OS X, 10.4.x anyway.
On Jan 28, 2009, at 8:01 AM, Daniel B. wrote:
user as a possible option. Would that work? I need to switch both
the user and group.

James Edward G. II

Does something like this not work for you?

def _change_privilege(user, group=user)
uid, gid = Process.euid, Process.egid

begin
target_uid = Etc.getpwnam(user).uid
rescue ArgumentError => e
return false
end

begin
target_gid = Etc.getgrnam(group).gid
rescue ArgumentError => e
return false
end

if (uid != target_uid) || (gid != target_gid)
# Change process ownership
Process.initgroups(user, target_gid)
Process::GID.change_privilege(target_gid)
Process::UID.change_privilege(target_uid)
end
true
rescue Errno::EPERM => e
false
end

Cheers-

Ezra Z.
[email protected]

On Jan 28, 2009, at 11:14 AM, Ezra Z. wrote:

Tips of TFM I should go R are welcome. :slight_smile:
another issue I’m fighting, but nothing about this issue.
shipping an application, so I’ve got to find some workaround. I’ve

target_gid = Etc.getgrnam(group).gid
true
rescue Errno::EPERM => e
false
end

This worked. Thanks so much Ezra.

James Edward G. II